Windows 10中的WPF ListBox高亮显示
我对WPF还是很陌生,但是对.NET(Winforms)很有经验.我正在尝试操纵列表框的突出显示样式,以控制所选项目的焦点和未焦点颜色.我发现的每个教程都使用自定义样式为SystemColors.HighlightBrushKey和SystemColors.ControlBrushKey分配新值.但这不起作用.经过无数小时的尝试,使它起作用后,我发现它可能与操作系统有关.我曾在Windows 10系统上尝试过它.我在Windows 7安装程序上运行了完全相同的代码,瞧瞧,它起作用了!
I'm fairly new to WPF but experienced in .NET (Winforms). I'm trying to manipulate the highlight style of a listbox to control the focused and unfocused color of the selected item. Every single tutorial on this that I have found uses a custom style to assign a new value to the SystemColors.HighlightBrushKey and SystemColors.ControlBrushKey. But it isn't working. After countless hours trying to get this to work, it occurred to me that maybe it was OS related. I had been trying it on a Windows 10 system. I ran the exact same code on a Windows 7 setup, and lo and behold, it worked!
因此,显然,旧方法在Windows 10中不起作用(至少对我来说是这样).有人找到替代品了吗?归根结底,我只希望列表框即使没有焦点也能保持高亮显示.默认的灰色高光很难看清,在某些用法中似乎不合适.我有一个现实世界的场景,当焦点从ListBox移开时,突出显示基本上消失非常不自然.
So apparently the old method doesn't work in Windows 10 (at least that's what it looks like to me). Has anybody found an alternative? At the end of the day, I just want the listbox to maintain the bright highlight even when it doesn't have focus. The default grey highlight is difficult to see, and doesn't seem appropriate in some usages. I have a real world scenario where it feels very unnatural for the highlight to basically disappear when the focus moves away from the ListBox.
下面是我使用的XAML代码,该代码在Windows 7上有效,但在Windows 10上无效.(顺便说一句,我还尝试用SystemColors.InactiveSelectionHighlightBrushKey替换SystemColors.ControlBrushKey -结果是相同的.)
Below is the XAML code I used that worked on Windows 7 but not on Windows 10. (By the way, I have also tried replacing SystemColors.ControlBrushKey with SystemColors.InactiveSelectionHighlightBrushKey -- the results were the same).
<Window x:Class="TestApp.TestWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:TestApp"
mc:Ignorable="d"
Title="TestWindow" Height="300" Width="300" Loaded="Window_Loaded">
<Window.Resources>
<Style x:Key="myListboxStyle">
<Style.Resources>
<!-- Background of selected item when focused -->
<SolidColorBrush x:Key="{x:Static SystemColors.HighlightBrushKey}" Color="Red" />
<!-- Background of selected item when not focused -->
<SolidColorBrush x:Key="{x:Static SystemColors.ControlBrushKey}" Color="Green" />
</Style.Resources>
</Style>
</Window.Resources>
<Grid>
<ListBox x:Name="listBox" Style="{StaticResource myListboxStyle}" HorizontalAlignment="Left" Height="100" Margin="22,18,0,0" VerticalAlignment="Top" Width="237">
<ListBoxItem>Test 1</ListBoxItem>
<ListBoxItem>Test 2</ListBoxItem>
<ListBoxItem>Test 3</ListBoxItem>
</ListBox>
<TextBox x:Name="textBox" HorizontalAlignment="Left" Height="23" Margin="50,165,0,0" TextWrapping="Wrap" Text="TextBox" VerticalAlignment="Top" Width="120"/>
</Grid>
</Window>
如果您确实要更改应用程序的默认设置,则始终可以通过制作模板副本来修改样式.在这种情况下,为ListBoxItem样式.
If you really want to change the defaults for your app, you can always modify the style by making a copy of the template. In this case ListBoxItem style.
在设计器中,单击ListBoxItem,右键单击编辑模板",然后编辑副本".
In the designer, click on a ListBoxItem, right click Edit Template, and Edit a Copy.
下面是我在计算机上获得的内容,以及使用红色/绿色运行的应用程序的屏幕快照,展示了应用于受影响项目的样式.您当然会将它应用于所有项目...
Below is what I got on my machine, and a screenshot of the app running with Red/Green demonstrating the style applied to affected items. You would of course apply this to all items...
<Window.Resources>
<Style x:Key="FocusVisual">
<Setter Property="Control.Template">
<Setter.Value>
<ControlTemplate>
<Rectangle Margin="2" SnapsToDevicePixels="true" Stroke="{DynamicResource {x:Static SystemColors.ControlTextBrushKey}}" StrokeThickness="1" StrokeDashArray="1 2"/>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
<SolidColorBrush x:Key="Item.MouseOver.Background" Color="#1F26A0DA"/>
<SolidColorBrush x:Key="Item.MouseOver.Border" Color="#a826A0Da"/>
<SolidColorBrush x:Key="Item.SelectedInactive.Background" Color="#3DDADADA"/>
<SolidColorBrush x:Key="Item.SelectedInactive.Border" Color="#FFDADADA"/>
<SolidColorBrush x:Key="Item.SelectedActive.Background" Color="#3D26A0DA"/>
<SolidColorBrush x:Key="Item.SelectedActive.Border" Color="#FF26A0DA"/>
<Style x:Key="ListBoxItemStyle1" TargetType="{x:Type ListBoxItem}">
<Setter Property="SnapsToDevicePixels" Value="True"/>
<Setter Property="Padding" Value="4,1"/>
<Setter Property="HorizontalContentAlignment" Value="{Binding HorizontalContentAlignment, RelativeSource={RelativeSource AncestorType={x:Type ItemsControl}}}"/>
<Setter Property="VerticalContentAlignment" Value="{Binding VerticalContentAlignment, RelativeSource={RelativeSource AncestorType={x:Type ItemsControl}}}"/>
<Setter Property="Background" Value="Transparent"/>
<Setter Property="BorderBrush" Value="Transparent"/>
<Setter Property="BorderThickness" Value="1"/>
<Setter Property="FocusVisualStyle" Value="{StaticResource FocusVisual}"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ListBoxItem}">
<Border x:Name="Bd" BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" Background="{TemplateBinding Background}" Padding="{TemplateBinding Padding}" SnapsToDevicePixels="true">
<ContentPresenter HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}" VerticalAlignment="{TemplateBinding VerticalContentAlignment}"/>
</Border>
<ControlTemplate.Triggers>
<MultiTrigger>
<MultiTrigger.Conditions>
<Condition Property="IsMouseOver" Value="True"/>
</MultiTrigger.Conditions>
<Setter Property="Background" TargetName="Bd" Value="{StaticResource Item.MouseOver.Background}"/>
<Setter Property="BorderBrush" TargetName="Bd" Value="{StaticResource Item.MouseOver.Border}"/>
</MultiTrigger>
<MultiTrigger>
<MultiTrigger.Conditions>
<Condition Property="Selector.IsSelectionActive" Value="False"/>
<Condition Property="IsSelected" Value="True"/>
</MultiTrigger.Conditions>
<Setter Property="Background" TargetName="Bd" Value="{StaticResource Item.SelectedInactive.Background}"/>
<Setter Property="BorderBrush" TargetName="Bd" Value="{StaticResource Item.SelectedInactive.Border}"/>
</MultiTrigger>
<MultiTrigger>
<MultiTrigger.Conditions>
<Condition Property="Selector.IsSelectionActive" Value="True"/>
<Condition Property="IsSelected" Value="True"/>
</MultiTrigger.Conditions>
<Setter Property="Background" TargetName="Bd" Value="{StaticResource Item.SelectedActive.Background}"/>
<Setter Property="BorderBrush" TargetName="Bd" Value="{StaticResource Item.SelectedActive.Border}"/>
</MultiTrigger>
<Trigger Property="IsEnabled" Value="False">
<Setter Property="TextElement.Foreground" TargetName="Bd" Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
<Style x:Key="ListBoxItemStyle2" TargetType="{x:Type ListBoxItem}">
<Setter Property="SnapsToDevicePixels" Value="True"/>
<Setter Property="Padding" Value="4,1"/>
<Setter Property="HorizontalContentAlignment" Value="{Binding HorizontalContentAlignment, RelativeSource={RelativeSource AncestorType={x:Type ItemsControl}}}"/>
<Setter Property="VerticalContentAlignment" Value="{Binding VerticalContentAlignment, RelativeSource={RelativeSource AncestorType={x:Type ItemsControl}}}"/>
<Setter Property="Background" Value="Transparent"/>
<Setter Property="BorderBrush" Value="Transparent"/>
<Setter Property="BorderThickness" Value="1"/>
<Setter Property="FocusVisualStyle" Value="{StaticResource FocusVisual}"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ListBoxItem}">
<Border x:Name="Bd" BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" Background="{TemplateBinding Background}" Padding="{TemplateBinding Padding}" SnapsToDevicePixels="true">
<ContentPresenter HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}" VerticalAlignment="{TemplateBinding VerticalContentAlignment}"/>
</Border>
<ControlTemplate.Triggers>
<MultiTrigger>
<MultiTrigger.Conditions>
<Condition Property="IsMouseOver" Value="True"/>
</MultiTrigger.Conditions>
<Setter Property="Background" TargetName="Bd" Value="{StaticResource Item.MouseOver.Background}"/>
<Setter Property="BorderBrush" TargetName="Bd" Value="{StaticResource Item.MouseOver.Border}"/>
</MultiTrigger>
<MultiTrigger>
<MultiTrigger.Conditions>
<Condition Property="Selector.IsSelectionActive" Value="False"/>
<Condition Property="IsSelected" Value="True"/>
</MultiTrigger.Conditions>
<Setter Property="Background" TargetName="Bd" Value="Red"/>
<Setter Property="BorderBrush" TargetName="Bd" Value="{StaticResource Item.SelectedInactive.Border}"/>
</MultiTrigger>
<MultiTrigger>
<MultiTrigger.Conditions>
<Condition Property="Selector.IsSelectionActive" Value="True"/>
<Condition Property="IsSelected" Value="True"/>
</MultiTrigger.Conditions>
<Setter Property="Background" TargetName="Bd" Value="Green"/>
<Setter Property="BorderBrush" TargetName="Bd" Value="{StaticResource Item.SelectedActive.Border}"/>
</MultiTrigger>
<Trigger Property="IsEnabled" Value="False">
<Setter Property="TextElement.Foreground" TargetName="Bd" Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</Window.Resources>
<Grid x:Name="LayoutRoot" Opacity="{Binding MainWindowOpacity}">
<StackPanel>
<TextBlock Text="WPF" FontSize="36" Margin="20" Foreground="Orange" HorizontalAlignment="Center"/>
<ListBox x:Name="listBox" HorizontalAlignment="Left" Height="100" VerticalAlignment="Top" Width="237">
<ListBoxItem Style="{DynamicResource ListBoxItemStyle1}">Test 1</ListBoxItem>
<ListBoxItem Style="{DynamicResource ListBoxItemStyle2}">Test 2</ListBoxItem>
<ListBoxItem>Test 3</ListBoxItem>
</ListBox>
</StackPanel>
</Grid>
运行中的应用程序:
有效:
无效:
偷闲者.