I have below button style in window resources:
<Style x:Key="MyStyle" TargetType="{x:Type Button}">
<Setter Property="BorderBrush" Value="Transparent"/>
<Setter Property="BorderThickness" Value="0 0 0 3"/>
<Style.Triggers>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="BorderBrush" Value="Orange" />
</Trigger>
<Trigger Property="IsPressed" Value="True">
<Setter Property="BorderBrush" Value="Red" />
</Trigger>
</Style.Triggers>
</Style>
This style is shared by two wpf buttons. But there is a button I want to show a custom color when it is pressed, the color will be green.
So in this special button I would like to override the value specified for borderbrush property in the trigger, instead of Red I would like Green.
How to do this?
You could set the BorderBrush property using a {DynamicResource} that you can override:
<SolidColorBrush x:Key="pressed" Color="Red" />
<Style x:Key="MyStyle" TargetType="{x:Type Button}">
<Setter Property="BorderBrush" Value="Transparent"/>
<Setter Property="BorderThickness" Value="0 0 0 3"/>
<Style.Triggers>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="BorderBrush" Value="Orange" />
</Trigger>
<Trigger Property="IsPressed" Value="True">
<Setter Property="BorderBrush" Value="{DynamicResource pressed}" />
</Trigger>
</Style.Triggers>
</Style>
...
<Button Content="Red" Style="{StaticResource MyStyle}" />
<Button Content="Green" Style="{StaticResource MyStyle}">
<Button.Resources>
<SolidColorBrush x:Key="pressed" Color="Green" />
</Button.Resources>
</Button>
Or you could create another Style that overrides the entire trigger:
<Button Content="Green">
<Button.Style>
<Style TargetType="Button" BasedOn="{StaticResource MyStyle}">
<Style.Triggers>
<Trigger Property="IsPressed" Value="True">
<Setter Property="Foreground" Value="Green" />
</Trigger>
</Style.Triggers>
</Style>
</Button.Style>
</Button>
Related
I have a custom Style for textbox, I apply DropShadowEffect and a border in this textbox, I would like to remove the effect of both the border and the Shadow when user clicks outside the wpf.
For example if a user has wpf open and clicks on the windows desktop, wpf should remove the border and shadow.
My Style:
<Style x:Key="MTextBox" TargetType="{x:Type TextBox}">
<Setter Property="BorderBrush" Value="White" />
<Style.Triggers>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="BorderThickness" Value="2" />
<Setter Property="BorderBrush" Value="Red" />
</Trigger>
<Trigger Property="IsFocused" Value="True">
<Setter Property="BorderThickness" Value="2" />
<Setter Property="BorderBrush" Value="Red" />
<Setter Property="Effect">
<Setter.Value>
<DropShadowEffect ShadowDepth="1" Color="Red" Opacity="1" BlurRadius="2"/>
</Setter.Value>
</Setter>
</Trigger>
</Style.Triggers>
Try property "IsKeyboardFocused" instead of "IsFocused" in your second trigger.
I use a template for my buttons. Now I got to a point where I want to change the template on runtime. But that doesn't work with this template.
The template looks like this:
<Application.Resources>
<Style TargetType="{x:Type Button}">
<Setter Property="OverridesDefaultStyle" Value="true"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type Button}">
<Border Name="Border" Background="Transparent">
<ContentPresenter RecognizesAccessKey="True"/>
</Border>
<ControlTemplate.Triggers>
<Trigger Property="IsKeyboardFocused" Value="true">
<Setter TargetName="Border" Property="BorderBrush" Value="#ffffff" />
</Trigger>
<Trigger Property="IsDefaulted" Value="true">
<Setter TargetName="Border" Property="BorderBrush" Value="#ffffff" />
</Trigger>
<Trigger Property="IsMouseOver" Value="true">
<Setter TargetName="Border" Property="Background" Value="Transparent" />
</Trigger>
<Trigger Property="IsPressed" Value="true">
<Setter TargetName="Border" Property="Background" Value="Transparent" />
<Setter TargetName="Border" Property="BorderBrush" Value="#ffffff" />
</Trigger>
<Trigger Property="IsEnabled" Value="false">
<Setter TargetName="Border" Property="Background" Value="Transparent" />
<Setter TargetName="Border" Property="BorderBrush" Value="#ffffff" />
<Setter Property="Foreground" Value="Transparent"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</Application.Resources>
I used it on different windows, therefore as application resource.
How do I access this template and change it for only some buttons?
I thought about creating different templates. But how do I create one where I can change things like Background, etc. on runtime?
If you give an x:key to your resource, you should be able to do something like this:
<Window.Resources>
<ResourceDictionary>
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary Source="/MyProject.Styles;component/ButtonStyles.xaml"/>
</ResourceDictionary.MergedDictionaries>
</ResourceDictionary>
</Window.Resources>
Then Just use :
<Button>
<Button.Style>
<Style BasedOn="{StaticResource StyleFromButtonStyles}" TargetType="Button">
And override with Style.Setter the property that you want to change
I have a styled window and I want to override a datagrid style to ALL datagrids in my application
<Window.Resources>
<Style x:Name="dtgStyle" TargetType="{x:Type DataGridRow}">
<Style.Triggers>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="Background" Value="Transparent" />
</Trigger>
<Trigger Property="IsSelected" Value="True">
<Setter Property="Background" Value="Blue" />
</Trigger>
<Trigger Property="IsSelected" Value="False">
<Setter Property="Background" Value="Transparent" />
</Trigger>
</Style.Triggers>
<Setter Property="Background" Value="Transparent" />
<Setter Property="Foreground" Value="White" />
</Style>
</Window.Resources>
I thougth this had to work but I have to apply
Style s = Resources["dtgStyle"] as Style;
mydtg.Style = s;
now I wouldn't like to have to apply that to ALL dtgs.
The best would be to automatically apply it in xaml.
Thanx
---ADD for ASh----
Thank you for your help. The only problem is that when the datagrid loses focus the selected line in the datagrid changes colour as you can see in the following pic (foreground turns to black).
I have tried to add various property but nothing works.
additionally the left border gets bolder (no pun intended) and larger.
Any idea how to fix it?
Thanks
if you need default style for FrameworkElement, declare it without x:Key, only with TargetType.
Both DataGridRow and DataGridCell have IsSelected property. Not enough to change Background only for DataGridRow, it has to be done for DataGridCell as well
<Style TargetType="{x:Type DataGrid}">
<Setter Property="RowStyle" >
<Setter.Value>
<Style TargetType="{x:Type DataGridRow}" BasedOn="{StaticResource {x:Type DataGridRow}}">
<Setter Property="Background" Value="Transparent" />
<Setter Property="Foreground" Value="White" />
<Style.Triggers>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="Background" Value="Transparent" />
</Trigger>
<Trigger Property="IsSelected" Value="True">
<Setter Property="Background" Value="Orange" />
<Setter Property="Foreground" Value="White" />
</Trigger>
</Style.Triggers>
</Style>
</Setter.Value>
</Setter>
<Setter Property="CellStyle">
<Setter.Value>
<Style TargetType="{x:Type DataGridCell}" BasedOn="{StaticResource {x:Type DataGridCell}}">
<Style.Triggers>
<Trigger Property="IsSelected" Value="True">
<Setter Property="Background" Value="Orange" />
</Trigger>
<DataTrigger Binding="{Binding IsKeyboardFocusWithin, RelativeSource={RelativeSource AncestorType={x:Type DataGrid}}}" Value="False">
<Setter Property="Foreground" Value="White"/>
</DataTrigger>
</Style.Triggers>
</Style>
</Setter.Value>
</Setter>
</Style>
fix for Foreground was found here: DataGrid's selected row color when inactive (https://stackoverflow.com/a/25204493/1506454)
I am new to Styles and not sure on the best way to create a Button style to change the Foreground of IsMouseOver and IsPressed. I used a Border for a template because it has a CornerRadius and background and border properties. But Border does not have a Foreground property. Using Button as the template doesn't work well since the default look isn't being overridden.
What is a better way to style a Button template with Foreground behavior? Maybe using a label inside the border?
Here is the App.xaml:
<Application.Resources>
<Style TargetType="Button" x:Key="MyButton">
<Setter Property="SnapsToDevicePixels" Value="true"/>
<Setter Property="OverridesDefaultStyle" Value="true"/>
<Setter Property="MinHeight" Value="34"/>
<Setter Property="Foreground" Value="White"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="Button">
<Border Name="shortcutbutton"
BorderThickness="1"
BorderBrush="Black"
Background="Gray">
<ContentPresenter Margin="2"
HorizontalAlignment="Center"
VerticalAlignment="Center"
RecognizesAccessKey="True"/>
</Border>
<ControlTemplate.Triggers>
<Trigger Property="IsMouseOver" Value="true">
<Setter TargetName="shortcutbutton" Property="Background" Value="#FFDADADA" />
<Setter TargetName="shortcutbutton" Property="BorderBrush" Value="#EEEEEE" />
<!--<Setter TargetName="Border" Property="Foreground" Value="Black" />-->
</Trigger>
<Trigger Property="IsPressed" Value="true">
<Setter TargetName="shortcutbutton" Property="Background" Value="DarkGray" />
<Setter TargetName="shortcutbutton" Property="BorderBrush" Value="Black" />
<!--<Setter TargetName="Border" Property="Foreground" Value="Red" />-->
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</Application.Resources>
And the xaml:
<StackPanel HorizontalAlignment="Center" Height="100" VerticalAlignment="Center" Width="100">
<Button Content="Button" Height="41" Style="{DynamicResource MyButton}"/>
</StackPanel>
You need to move your Triggers from the ControlTemplate to the Style. Something like this:
<Style TargetType="Button">
<Setter Property="SnapsToDevicePixels" Value="true"/>
<Setter Property="OverridesDefaultStyle" Value="true"/>
<Setter Property="MinHeight" Value="34"/>
<Setter Property="Foreground" Value="White"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="Button">
<Border Name="shortcutbutton"
BorderThickness="1"
BorderBrush="Black"
Background="Gray">
<ContentPresenter Margin="2"
HorizontalAlignment="Center"
VerticalAlignment="Center"
RecognizesAccessKey="True"/>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
<Style.Triggers>
<Trigger Property="IsMouseOver" Value="true">
<Setter Property="Foreground" Value="#FFDADADA" />
</Trigger>
<Trigger Property="IsPressed" Value="true">
<Setter Property="Foreground" Value="DarkGray" />
</Trigger>
</Style.Triggers>
</Style>
What you can do is set attached property of TextElement on the Border and like that every text element within your Border will be of that colour:
<ControlTemplate.Triggers>
<Trigger Property="IsMouseOver" Value="true">
<Setter TargetName="shortcutbutton" Property="Background" Value="#FFDADADA" />
<Setter TargetName="shortcutbutton" Property="BorderBrush" Value="#EEEEEE" />
<Setter TargetName="shortcutbutton" Property="TextElement.Foreground" Value="White"/>
</Trigger>
...
</ControlTemplate.Triggers>
I have create a style for a button like this
<Style TargetType="{x:Type Button}" x:Key="BoutonRessources">
<Setter Property="Width" Value="18" />
<Setter Property="Margin" Value="-1,0,-2,0" />
<Setter Property="ToolTip" Value="Clear" />
<Setter Property="VerticalAlignment" Value="Center" />
<Setter Property="BorderThickness" Value="0" />
<Setter Property="HorizontalAlignment" Value="Center" />
<Setter Property="Background" Value="Transparent" />
<Setter Property="HorizontalContentAlignment" Value="Center" />
<Style.Triggers>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="Background">
<Setter.Value>
<ImageBrush ImageSource="BoutonToolbarSelected.png"/>
</Setter.Value>
</Setter>
<Setter Property="Height" Value="22"/>
<Setter Property="Width" Value="32"/>
</Trigger>
</Style.Triggers>
</Style>
My button appear on my screen but when the mouse is over the button, it don't show my "BoutonToolbarSelected.png". Do you know why ?
Here is how i call my button :
<Button Style="{StaticResource BoutonRessources}" >
<Image Source= "xRtDiva_XWPF_TBR_PREMIER.PNG_IMAGES.png" Height="18"/>
</Button>
Thanks a lot :)
Because you set <Image Source= "xRtDiva_XWPF_TBR_PREMIER.PNG_IMAGES.png" Height="18"/> as Content of your button, the background will hide behind it.
You could change your trigger to:
<Style.Triggers>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="Background">
<Setter.Value>
<ImageBrush ImageSource="BoutonToolbarSelected.png"/>
</Setter.Value>
</Setter>
<Setter Property="Height" Value="22"/>
<Setter Property="Width" Value="32"/>
</Trigger>
<Trigger Property="IsMouseOver" Value="False">
<Setter Property="Background">
<Setter.Value>
<ImageBrush ImageSource="xRtDiva_XWPF_TBR_PREMIER.PNG_IMAGES.png"/>
</Setter.Value>
</Setter>
<Setter Property="Height" Value="18"/>
</Trigger>
</Style.Triggers>