wpf - style 根据背景颜色选择合适的前景

标签 wpf styles background-color foreground

我有一个 WPF 应用程序,它带有一组由项目类型定义的标签、文本框等默认样式(未定义显式键)。

在该应用程序中,使用了两个主要容器,一个具有深色背景,一个具有浅色背景,因此有时使用黑色作为 Label 的前景色是正确的,有时则大错特错。另一方面,编辑器的样式总是相当传统,浅色背景和深色前景,所以我不能将所有子元素的前景设置为相反的。

是否有一种优雅的方式让我的标签(可能还有 TextBlocks)根据“它们的”背景来决定它们的前景色?我只想在两种颜色之间切换,因此不需要自动对比度最大化,只需要一些阈值来避免白色背景上出现白色字体。

我也不想定义两组默认​​样式,我极力寻找某种方法使我的单个 Label-Default-Style 适用于两种背景变体。

是否有可能(并且在没有太多性能影响的情况下可行)向样式添加触发器/绑定(bind)以评估当前背景颜色?

或者,我会对如何为某些 FrameworkElements(尤其是容器/面板)干净地设置背景颜色的最佳实践感兴趣,而不会遇到上述问题。

这是我尝试过的(当然是经过简化的):

  <UniformGrid>
  <UniformGrid.Resources>
  <!-- SimpleStyles: Label -->
     <Style x:Key="{x:Type Label}" TargetType="{x:Type Label}">
        <Setter Property="HorizontalContentAlignment" Value="Left"/>
        <Setter Property="VerticalContentAlignment" Value="Top"/>
        <Setter Property="Template">
           <Setter.Value>
              <ControlTemplate TargetType="{x:Type Label}">
                 <Border>
                    <ContentPresenter HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" VerticalAlignment="{TemplateBinding VerticalContentAlignment}" RecognizesAccessKey="True"/>
                 </Border>
                 <ControlTemplate.Triggers>
                    <Trigger Property="Background" Value="Black">
                       <Setter Property="Foreground" Value="Red"/>
                    </Trigger>
                    <Trigger Property="IsEnabled" Value="false">
                       <Setter Property="Foreground" Value="#888888"/>
                    </Trigger>
                 </ControlTemplate.Triggers>
              </ControlTemplate>
           </Setter.Value>
        </Setter>
     </Style>
  </UniformGrid.Resources>
  <Label x:Name="bgSetExplicitly" Background="Black">abc
  </Label>
  <Border Background="Black">
     <Label x:Name="bgInheritedFromParent" >abc
     </Label>
  </Border>
  <Label>abc
  </Label>
  <Label>abc
  </Label>

您可以看到标签的背景选择得很好,如果标签有明确的背景集(x:Name=bgSetExplicitly),但如果背景是从 VisualTree 中的父级“继承”的(x:Name="bgInheritedFromParent"), 它不是。 我很乐意让样式能够评估“有效背景”(无论它来自何处)并为此背景选择合适的前景画笔。

最佳答案

这个问题似乎暗示着更深层次的问题。我猜你还没有整合前景色的管理,所以你有一个应用程序的代码或样式在各处设置前景色。现在您正在处理其中的一个影响。

我会面对更深层次的问题并解决它。我真的不明白你为什么抵制创建默认样式的想法,但暂时假设你有充分的理由不这样做(除了“我应该在某个时候创建​​默认样式,但现在我还没有,我的应用程序已经变大了,这太难了,”在这种情况下,我有不同的建议),创建全局资源怎么样?

在应用程序的资源字典中为控件的前景色和背景色创建对象,并修复 XAML,使其不再直接引用画笔,而是使用 DynamicResource 标记扩展从资源中获取它们字典。在代码中,不是直接将控件的 Foreground 属性设置为画笔,而是使用 GetResource 获取画笔。并以同样的方式设置背景。

完成此操作后,如果您想在应用程序中全局更改前景色/背景色,只需更改资源即可。

这基本上就是您开始制作可设置皮肤的 WPF 应用程序的方式,这似乎是您要走的路。

关于wpf - style 根据背景颜色选择合适的前景,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6186344/

相关文章:

c# - 在 XAML ResourceDictionary 中绑定(bind)

javascript - 你如何确定 JavaScript 中的媒体类型?

swift - 无法根据背景颜色快速更改单元格高度

android - 如何重置单选按钮的背景颜色?

WPF 获取 UserControl 所有者(容器元素)

c# - View 的创建应该是 View 或 ViewModel [MVVM] 的一部分?

wpf - InvalidDeploymentException-未设置应用程序身份

html - 如何在不使用 <span> 标记的情况下从 CSS 文件替换 <h1> 中的文本?

c# - WPF - 我可以使用常量作为资源键名称吗?

jquery - 改变div的背景颜色一段时间,然后返回到上一个