
你好
我现在尝试了 2 天多来创建像上图一样处于按下状态的切换按钮,但是上边框让我很头疼。有谁知道如何创建下降的圆角?背景是从上到下的线性渐变:#b8c7d6 - #a8b3c4
任何帮助都将不胜感激!
我有这样的东西,但它与设计相去甚远:
<Style x:Key="ToggleButtonStyle" TargetType="{x:Type ToggleButton}">
<Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.ControlTextBrushKey}}"/>
<Setter Property="HorizontalContentAlignment" Value="Center"/>
<Setter Property="VerticalContentAlignment" Value="Center"/>
<Setter Property="Padding" Value="1"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ToggleButton}">
<Grid>
<Border Background="Black" BorderThickness="1" BorderBrush="#FF4E4F50" CornerRadius="3"/>
<Border Background="Black" Margin="1" CornerRadius="3"/>
<Border Margin="2" CornerRadius="3">
<Border.Background>
<LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
<GradientStop Color="#0099B9D1" Offset="0"/>
<GradientStop Color="#FF99B9D1" Offset="1"/>
<GradientStop Color="#B299B9D1" Offset="0.054"/>
</LinearGradientBrush>
</Border.Background>
</Border>
<Border Margin="2" CornerRadius="3" Opacity="0.3">
<Border.Background>
<LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
<LinearGradientBrush.RelativeTransform>
<TransformGroup>
<ScaleTransform CenterY="0.5" CenterX="0.5"/>
<SkewTransform CenterY="0.5" CenterX="0.5"/>
<RotateTransform Angle="90" CenterY="0.5" CenterX="0.5"/>
<TranslateTransform/>
</TransformGroup>
</LinearGradientBrush.RelativeTransform>
<GradientStop Color="Black" Offset="0"/>
<GradientStop Color="Black" Offset="1"/>
<GradientStop Color="#00090909" Offset="0.022"/>
<GradientStop Color="#00000000" Offset="0.99"/>
<GradientStop Color="#45060606" Offset="0.001"/>
</LinearGradientBrush>
</Border.Background></Border>
<ContentPresenter HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" Margin="{TemplateBinding Padding}" RecognizesAccessKey="True" SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}" VerticalAlignment="{TemplateBinding VerticalContentAlignment}"/>
</Grid>
<ControlTemplate.Triggers>
<Trigger Property="IsKeyboardFocused" Value="true">
</Trigger>
<Trigger Property="IsChecked" Value="true">
</Trigger>
<Trigger Property="IsEnabled" Value="false">
<Setter Property="Foreground" Value="#ADADAD"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
Run Code Online (Sandbox Code Playgroud)
以下是对我有用的方法。我发现圆角在正确创建顶部区域阴影方面增加了一些额外的挑战,但我能够通过结合多种技术来实现这一目标。
第一种技术涉及巧妙使用两个边框。外边框有其ClipToBounds设置为true,内部边界具有DropShadowEffect与ShadowDepth设置为0,BlurRadius大约5。这会让我们的正是我们需要的部分,但不会处理圆角问题(我们会得到到那个)。可以在本文中找到此技术。这是它的要点:
<Border BorderBrush="DarkGray" BorderThickness="1" ClipToBounds="True">
<Border BorderBrush="Black" BorderThickness="1" Margin="-1">
<Border.Effect>
<DropShadowEffect ShadowDepth="0" BlurRadius="6">
</Border.Effect>
</Border>
</Border>
Run Code Online (Sandbox Code Playgroud)
如果我没记错的话,在这一点上,我们会得到接近你想要的东西,除了DropShadowEffect圆角的“出血”(我们很快会再次解决这个问题)。
我们现在遇到的另一个问题是,我们放置在内部的任何子元素Border也将DropShadowEffect应用于它们!为了纠正这个问题,我们需要第二种技术。将两个Borders以及另一个容器(用于保存您的内容)放入一个 中Grid,以便外部Border容器和新容器是同级的。这将导致兄弟姐妹彼此重叠,而仅施加DropShadowEffect到Border。看到这个答案。
现在要解决“流血”问题,其中DropShadowEffect不遵循圆角的轮廓,而是表现得好像角是直的。这需要第三种技术。我们需要使用Michah 的 ClippingBorder自定义控件。我们需要Border用 his替换上面提到的外部控件ClippingBorder,仍然保持ClipToBounds设置为 true。这将修剪圆角处的出血。
我能够结合这三种技术来创建“下沉”(或“插入”)边框外观。它看起来像:
<Grid>
<local:ClippingBorder x:Name="TopShadowClippingBorder"
BorderThickness="0"
CornerRadius="5"
ClipToBounds="True">
<Border x:Name="TopShadowBorder"
BorderBrush="#D8333333" BorderThickness=".5,1,.5,0"
Padding="0"
CornerRadius="5"
ClipToBounds="True">
<Border.Effect>
<DropShadowEffect Direction="270" ShadowDepth="0.5"/>
</Border.Effect>
</Border>
</local:ClippingBorder>
<Border x:Name="InsetBorder"
BorderBrush="#99A1A1A1" BorderThickness="0.5,0,0.5,1"
CornerRadius="5" />
<StackPanel x:Name="Contents_StackPanel" Orientation="Horizontal" Margin="5,5,5,5">
(Contents go here...)
</StackPanel>
</Grid>
Run Code Online (Sandbox Code Playgroud)
请注意,上面的“发光”(DropShadowEffect)很好地遵循了边框圆角的轮廓:

我会使用两个边框:外部看起来像:
<Border CornerRadius="3" BorderBrush="White" BorderThickness="1">
Run Code Online (Sandbox Code Playgroud)
内部将创建阴影效果,如下所示:
<Border CornerRadius="3" BorderThickness="2,4,2,0">
<Border.BorderBrush>
<LinearGradientBrush StartPoint="0,0" EndPoint="0,1">
<GradientStop Offset="0" Color="Black"/>
<GradientStop Offset="0.2" Color="#00000000"/>
</LinearGradientBrush>
</Border.BorderBrush>
Run Code Online (Sandbox Code Playgroud)
显然,您需要调整这些值,但这至少应该产生您想要的效果。