ToggleButton: Style doesn't work with IsChecked binding - c#

I have a ToggleButton defined like this:
<ToggleButton x:Name="tbtn_delivery_advice" IsChecked="{Binding ServiceOptions.Advice.Requested}" Style="{DynamicResource ToggleButtonStyle}" Grid.Column="0" Grid.Row="1" Width="28" Margin="2 7" VerticalAlignment="Top"/>
and this style, that I found on the internet:
<Style x:Key="ToggleButtonStyle" TargetType="{x:Type ToggleButton}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ToggleButton}">
<Viewbox>
<Border x:Name="Border" CornerRadius="10"
Background="#FFFFFFFF"
Width="40" Height="20"
BorderBrush="#FF707070"
BorderThickness="1">
<Ellipse x:Name="Ellipse" Fill="#FFFFFFFF" Stretch="Uniform"
Margin="2 1 2 1"
Stroke="LightGray" StrokeThickness="1"
HorizontalAlignment="Stretch">
</Ellipse>
</Border>
</Viewbox>
<ControlTemplate.Triggers>
<EventTrigger RoutedEvent="Checked">
<BeginStoryboard>
<Storyboard>
<ColorAnimation Storyboard.TargetName="Border"
Storyboard.TargetProperty="(Border.Background).(SolidColorBrush.Color)"
To="#FF4CD661"
Duration="0:0:0.1" />
<ThicknessAnimation Storyboard.TargetName="Ellipse"
Storyboard.TargetProperty="Margin"
To="20 1 2 1"
Duration="0:0:0.1" />
</Storyboard>
</BeginStoryboard>
</EventTrigger>
<EventTrigger RoutedEvent="Unchecked">
<BeginStoryboard>
<Storyboard>
<ColorAnimation Storyboard.TargetName="Border"
Storyboard.TargetProperty="(Border.Background).(SolidColorBrush.Color)"
To="White"
Duration="0:0:0.1" />
<ThicknessAnimation Storyboard.TargetName="Ellipse"
Storyboard.TargetProperty="Margin"
To="2 1 2 1"
Duration="0:0:0.1" />
</Storyboard>
</BeginStoryboard>
</EventTrigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
The Button works just fine and looks like expected when IsChecked is not bound to anything or to a property with an initial value of false. But as soon as the initial value is true I get an exception. The message states that the name Border can't be found in System.Windows.Controls.ControlTemplate.
I have no idea how to solve this problem and would appreciate any help.

I found a solution even thought I'm still not a hundred percent sure what the problem was.
I thought it may be, that the Checked event trigger gets called before the button is fully initialized. So I simply switched from EventTrigger to Trigger and now everything works fine.
This is my working style:
<Style x:Key="ToggleButtonStyle" TargetType="{x:Type ToggleButton}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ToggleButton}">
<Viewbox>
<Border x:Name="Border" CornerRadius="10"
Background="#FFFFFFFF"
Width="40" Height="20"
BorderBrush="#FF707070"
BorderThickness="1">
<Ellipse x:Name="Ellipse" Fill="#FFFFFFFF" Stretch="Uniform"
Margin="2 1 2 1"
Stroke="LightGray" StrokeThickness="1"
HorizontalAlignment="Stretch">
</Ellipse>
</Border>
</Viewbox>
<ControlTemplate.Triggers>
<Trigger Property="ToggleButton.IsChecked" Value="True">
<Trigger.EnterActions>
<BeginStoryboard>
<Storyboard>
<ColorAnimation Storyboard.TargetName="Border"
Storyboard.TargetProperty="(Border.Background).(SolidColorBrush.Color)"
To="#FF4CD661"
Duration="0:0:0.1" />
<ThicknessAnimation Storyboard.TargetName="Ellipse"
Storyboard.TargetProperty="Margin"
To="20 1 2 1"
Duration="0:0:0.1" />
</Storyboard>
</BeginStoryboard>
</Trigger.EnterActions>
<Trigger.ExitActions>
<BeginStoryboard>
<Storyboard>
<ColorAnimation Storyboard.TargetName="Border"
Storyboard.TargetProperty="(Border.Background).(SolidColorBrush.Color)"
To="White"
Duration="0:0:0.1" />
<ThicknessAnimation Storyboard.TargetName="Ellipse"
Storyboard.TargetProperty="Margin"
To="2 1 2 1"
Duration="0:0:0.1" />
</Storyboard>
</BeginStoryboard>
</Trigger.ExitActions>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>

Related

How to make blinking rectangle stroke in WPF

Below my rectangle in WPF:
<Rectangle Margin="5,0" HorizontalAlignment="Left" Width="380" Height="25" Fill="LightYellow" Stroke="Orange" StrokeThickness="2" RadiusX="8" RadiusY="8"/>
I would like to start bliking for some seconds (and then stop) the rectangle stroke property when a property "StartBlinking" in view model changes from false to true.
I would like to implement storyboard in xaml not in c# code.
How can I do this?
I have tried this but not working:
<Rectangle Margin="5,0" HorizontalAlignment="Left" Width="380" Height="25" Fill="LightYellow" Stroke="Orange" StrokeThickness="2" RadiusX="8" RadiusY="8">
<Rectangle.Style>
<Style TargetType="{x:Type Rectangle}">
<Style.Resources>
<Storyboard x:Key="flashAnimation" >
<DoubleAnimation Storyboard.TargetProperty="Stroke" From="1" To="0" AutoReverse="True" Duration="0:0:0.5" RepeatBehavior="Forever" />
</Storyboard>
</Style.Resources>
</Style>
</Rectangle.Style>
</Rectangle>
I am using C# and .NET 3.5 in Visual Studio 2008.
You could animate the Opacity property of the Stroke using a DataTrigger and a Storyboard:
<Rectangle Margin="5,0" HorizontalAlignment="Left" Width="380" Height="25" Fill="LightYellow"
Stroke="Orange" StrokeThickness="2" RadiusX="8" RadiusY="8">
<Rectangle.Style>
<Style TargetType="Rectangle">
<Style.Triggers>
<DataTrigger Binding="{Binding StartBlinking}" Value="True">
<DataTrigger.EnterActions>
<BeginStoryboard>
<Storyboard>
<DoubleAnimation Storyboard.TargetProperty="Stroke.(SolidColorBrush.Opacity)"
To="0" AutoReverse="True" Duration="0:0:0.5" RepeatBehavior="6x" />
</Storyboard>
</BeginStoryboard>
</DataTrigger.EnterActions>
<DataTrigger.ExitActions>
<BeginStoryboard>
<Storyboard>
<DoubleAnimation Storyboard.TargetProperty="Stroke.(SolidColorBrush.Opacity)"
To="1" Duration="0:0:0.5" />
</Storyboard>
</BeginStoryboard>
</DataTrigger.ExitActions>
</DataTrigger>
</Style.Triggers>
</Style>
</Rectangle.Style>
</Rectangle>

Apply animation on WPF control visibility change

My xaml is
<Grid DockPanel.Dock="Top" >
<DockPanel Background="#bdbec0" MouseEnter="showTopMenu_MouseEnter" HorizontalAlignment="Stretch" Height="55" >
<Button HorizontalAlignment="Center" VerticalAlignment="Center">Down</Button>
</DockPanel>
<DockPanel Background="#151515" LastChildFill="True" Visibility="Collapsed" Name="TopMenuArea" Height="55">
some controls here in a horizontal strip , by default its hidden and when some one click on top button its visible and it wil be hidden when some one click outside this area
</DockPanel>
And code for button mouse over is
private void showTopMenu_MouseEnter(object sender, MouseEventArgs e)
{
TopMenuArea.Visibility = Visibility.Visible;
}
How can i apply a animation effect while changing the visibility of TopMenuArea ? Is any way to do it from xaml directly?
Eventtrigger
<DockPanel Background="#bdbec0" MouseEnter="showTopMenu_MouseEnter" HorizontalAlignment="Stretch" Height="55" >
<DockPanel.Triggers>
<EventTrigger RoutedEvent="DockPanel.MouseEnter">
<BeginStoryboard>
<Storyboard>
<DoubleAnimation Storyboard.TargetProperty="Opacity" Storyboard.TargetName="TopMenuArea"
From="0.0" To="1.0" Duration="0:0:1"></DoubleAnimation>
</Storyboard>
</BeginStoryboard>
</EventTrigger>
<EventTrigger RoutedEvent="DockPanel.MouseLeave">
<BeginStoryboard>
<Storyboard>
<DoubleAnimation Storyboard.TargetProperty="Opacity" Storyboard.TargetName="TopMenuArea"
From="1.0" To="0" Duration="0:0:1"></DoubleAnimation>
</Storyboard>
</BeginStoryboard>
</EventTrigger>
</DockPanel.Triggers>
<Button HorizontalAlignment="Center" VerticalAlignment="Center">Down</Button>
</DockPanel>
<DockPanel Background="#151515" LastChildFill="True" Visibility="Collapsed" Opacity="0" Name="TopMenuArea" Height="55">
</DockPanel>
Or use a style for fade in and out (with mouse enter / exit eventhandler like you did it)
<Style TargetType="FrameworkElement" x:Key="VisibleAnimation">
<Setter Property="Visibility" Value="Collapsed"/>
<Setter Property="Opacity" Value="0"/>
<Style.Triggers>
<Trigger Property="Visibility" Value="Visible">
<Trigger.EnterActions>
<BeginStoryboard>
<Storyboard>
<DoubleAnimation Storyboard.TargetProperty="Opacity"
From="0.0" To="1.0" Duration="0:0:0.2"/>
</Storyboard>
</BeginStoryboard>
</Trigger.EnterActions>
</Trigger>
</Style.Triggers>
</Style>
<DockPanel Background="#151515" LastChildFill="True" Style="{StaticResource VisibleAnimation}" Name="TopMenuArea" Height="55">
Just define the style in your App Resources, or in the local Window or UserControl. You reuse the Animation style for any control.
use this in your Stackpanel
<StackPanel Background="Red" HorizontalAlignment="Stretch" >
<StackPanel.Triggers>
<EventTrigger RoutedEvent="StackPanel.MouseLeftButtonDown" >
<BeginStoryboard>
<Storyboard>
<DoubleAnimation Storyboard.TargetProperty="Opacity" Storyboard.TargetName="TopMenuArea"
From="1.0" To="0" Duration="0:0:1"></DoubleAnimation>
<ObjectAnimationUsingKeyFrames Storyboard.TargetName="TopMenuArea"
Storyboard.TargetProperty="Visibility">
<DiscreteObjectKeyFrame KeyTime="0:0:2" Value="{x:Static Visibility.Collapsed}"/>
</ObjectAnimationUsingKeyFrames>
</Storyboard>
</BeginStoryboard>
</EventTrigger>
</StackPanel.Triggers>
<Label HorizontalAlignment="Center">Area outside top panel . Clicking here will hide top panel again</Label>
</StackPanel>
It's an old question, but I've put together an open source library to allow fading and/or translation on Visibility changed, Loaded or binding.
You can find it at SciChart.Wpf.UI.Transitionz on Github and on NuGet.
Usage:
<Window x:Class="WpfApplication15.MainWindow"
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:tz="http://schemas.abtsoftware.co.uk/transitionz"
mc:Ignorable="d"
Title="MainWindow" Height="350" Width="525">
<Window.Resources>
<BooleanToVisibilityConverter x:Key="b2vc"></BooleanToVisibilityConverter>
</Window.Resources>
<Grid>
<CheckBox x:Name="CheckBox" Content="Is Visible?" IsChecked="False"></CheckBox>
<TextBlock Text="Hello World!" FontSize="44" HorizontalAlignment="Center" VerticalAlignment="Center"
Visibility="Collapsed"
tz:Transitionz.Opacity="{tz:OpacityParams From=0, To=1, Duration=200, TransitionOn=Visibility}"
tz:Transitionz.Translate="{tz:TranslateParams From='10,0', To='0,0', Duration=200, TransitionOn=Visibility}"
tz:Transitionz.Visibility="{Binding ElementName=CheckBox, Path=IsChecked, Converter={StaticResource b2vc}}"/>
</Grid>
</Window>
Which results in:
This would be a good start.
You can just add one c# file and set property like below.
common:VisibilityAnimation.AnimationType="Fade"
here is a sample example
<Grid DockPanel.Dock="Top">
<DockPanel Background="#bdbec0"
x:Name="topPanel"
HorizontalAlignment="Stretch"
Height="55">
<Button HorizontalAlignment="Center"
VerticalAlignment="Center">Down</Button>
</DockPanel>
<DockPanel Background="#151515"
LastChildFill="True"
Name="TopMenuArea"
IsHitTestVisible="False"
Height="55">
<TextBlock Foreground="White"> some controls here in a horizontal strip , by default its hidden and when some one click on top button its visible and it wil be hidden when some one click outside this area</TextBlock>
<DockPanel.Style>
<Style TargetType="DockPanel">
<Setter Property="Opacity"
Value="0" />
<Style.Triggers>
<DataTrigger Binding="{Binding IsMouseOver,ElementName=topPanel}"
Value="true">
<Setter Property="Opacity"
Value="1" />
</DataTrigger>
</Style.Triggers>
</Style>
</DockPanel.Style>
</DockPanel>
</Grid>
in the sample above I have set IsHitTestVisible="False" on the TopMenuArea dockPanel, as i can see that it is on top of previous (source for trigger panel)
other option is to use the TopMenuArea as the source if it is on the top
sample
<Grid DockPanel.Dock="Top">
<DockPanel Background="#bdbec0"
HorizontalAlignment="Stretch"
Height="55">
<Button HorizontalAlignment="Center"
VerticalAlignment="Center">Down</Button>
</DockPanel>
<DockPanel Background="#151515"
LastChildFill="True"
Name="TopMenuArea"
Height="55">
<TextBlock Foreground="White"> some controls here in a horizontal strip , by default its hidden and when some one click on top button its visible and it wil be hidden when some one click outside this area</TextBlock>
<DockPanel.Style>
<Style TargetType="DockPanel">
<Setter Property="Opacity"
Value="0" />
<Style.Triggers>
<Trigger Property="IsMouseOver"
Value="true">
<Setter Property="Opacity"
Value="1" />
</Trigger>
</Style.Triggers>
</Style>
</DockPanel.Style>
</DockPanel>
</Grid>
give it a try and see if it is close to what you are looking for.
both of above just switch the opacity between 0 & 1, you may also use animation to make a fade effect if needed.
I come up with a way to gradually show Grid and hide Grid using ScaleTransform.
The ScaleTransform is set to X=0 Y=0 to hide, X=1 Y=1 to show,
and Trigger using Tag property, as the code below:
At ViewModel:
private string _helpVisiblilityTag = "hide";
public string HelpVisiblilityTag
{
get { return _helpVisiblilityTag; }
set
{
_helpVisiblilityTag = value;
NotifyOfPropertyChange(() => HelpVisiblilityTag);
}
}
public void Hide()
{
HelpVisiblilityTag = "hide";
}
public void Show()
{
HelpVisiblilityTag = "show";
}
At View:
<Button Click="Show"/>
<Grid VerticalAlignment="Center" HorizontalAlignment="Center" Tag="{Binding HelpVisiblilityTag}"
RenderTransformOrigin="0.5, 0.5" >
<Grid.Background>
<SolidColorBrush Color="#D4F1FA" Opacity="0.8"/>
</Grid.Background>
<Grid.RenderTransform>
<ScaleTransform x:Name="MyAnimatedScaleTransform"
ScaleX="0" ScaleY="0" />
</Grid.RenderTransform>
<Grid.Style>
<Style TargetType="{x:Type Grid}">
<Style.Triggers>
<Trigger Property="Tag" Value="show">
<Trigger.EnterActions>
<BeginStoryboard>
<Storyboard>
<DoubleAnimation Storyboard.TargetProperty="Opacity"
From="0.0" To="1.0" Duration="0:0:1" AutoReverse="False" />
<DoubleAnimation
Storyboard.TargetProperty="(UIElement.RenderTransform).(ScaleTransform.ScaleX)"
From="0.0" To="1" Duration="0:0:1" AutoReverse="False"
>
<DoubleAnimation.EasingFunction>
<ElasticEase EasingMode="EaseOut" Oscillations="1"/>
</DoubleAnimation.EasingFunction>
</DoubleAnimation>
<DoubleAnimation
Storyboard.TargetProperty="(UIElement.RenderTransform).(ScaleTransform.ScaleY)"
From="0.0" To="1" Duration="0:0:1" AutoReverse="False"
>
<DoubleAnimation.EasingFunction>
<ElasticEase EasingMode="EaseOut" Oscillations="1"/>
</DoubleAnimation.EasingFunction>
</DoubleAnimation>
</Storyboard>
</BeginStoryboard>
</Trigger.EnterActions>
<Trigger.ExitActions>
<BeginStoryboard>
<Storyboard>
<DoubleAnimation Storyboard.TargetProperty="Opacity"
Duration="0:0:0.5" AutoReverse="False" />
<DoubleAnimation
Storyboard.TargetProperty="(UIElement.RenderTransform).(ScaleTransform.ScaleX)"
From="1" To="0.0" Duration="0:0:0.5" AutoReverse="False"
/>
<DoubleAnimation
Storyboard.TargetProperty="(UIElement.RenderTransform).(ScaleTransform.ScaleY)"
From="1" To="0.0" Duration="0:0:0.5" AutoReverse="False"
/>
</Storyboard>
</BeginStoryboard>
</Trigger.ExitActions>
</Trigger>
</Style.Triggers>
</Style>
</Grid.Style>
<Button Click="Hide"/>
</Grid>
Sample Screenshot:
You can use ToggleButton Checked and UnChecked Routed Event with Event Trigger:
<ToggleButton Content="Toggle" Height="20" Width="60" Panel.ZIndex="2" VerticalAlignment="Top" HorizontalAlignment="Left">
<ToggleButton.Triggers>
<EventTrigger RoutedEvent="ToggleButton.Checked">
<BeginStoryboard>
<Storyboard >
<DoubleAnimation Storyboard.TargetName="MyDockPanel"
Storyboard.TargetProperty="Opacity"
From="0" To="1"
Duration="0:0:0.2"/>
</Storyboard>
</BeginStoryboard>
</EventTrigger>
<EventTrigger RoutedEvent="ToggleButton.Unchecked">
<BeginStoryboard>
<Storyboard>
<DoubleAnimation Storyboard.TargetName="MyDockPanel"
Storyboard.TargetProperty="Opacity"
From="1" To="0"
Duration="0:0:0.2"/>
</Storyboard>
</BeginStoryboard>
</EventTrigger>
</ToggleButton.Triggers>
</ToggleButton>
<DockPanel x:Name="MyDockPanel" Background="Yellow" Opacity="0">
<TextBlock DockPanel.Dock="Bottom" Text="DockPanel"
VerticalAlignment="Center" HorizontalAlignment="Center"/>
</DockPanel>
Result:

WPF XAML How can I conditionally perform this animation?

How do I conditionally get this animation to run, depending on a bool CanAnimate? It works right now, but I don't always want it to be animated, I want to check the boolean.
<Border BorderBrush="Black" BorderThickness="2" Margin="1" Name="ReviewNote">
<Border.Triggers>
<EventTrigger RoutedEvent="Border.Loaded">
<BeginStoryboard>
<Storyboard>
<DoubleAnimation
Storyboard.TargetName="ReviewNote"
Storyboard.TargetProperty="(Border.Opacity)"
From="1.0" To="0.0" AutoReverse="True" RepeatBehavior="Forever" />
</Storyboard>
</BeginStoryboard>
</EventTrigger>
</Border.Triggers>
<TextBlock Text="{x:Static Constants:StringConstants.ReviewNote}"
Background="{StaticResource ReviewNoteColor}" Width="100"
TextAlignment="Center" />
</Border>
Apply style on your border and inside style you can check value of bool property. Based on that property you can specify DataTrigger.EnterActions with storyboard after removing TargetName from storyBoard.
This will work -
<Border BorderBrush="Black" BorderThickness="2" Margin="1" Name="ReviewNote">
<Border.Style>
<Style TargetType="Border">
<Style.Triggers>
<DataTrigger Binding="{Binding CanAnimate}" Value="True">
<DataTrigger.EnterActions>
<BeginStoryboard>
<Storyboard>
<DoubleAnimation
Storyboard.TargetProperty="(Border.Opacity)"
From="1.0" To="0.0" AutoReverse="True"
RepeatBehavior="Forever" />
</Storyboard>
</BeginStoryboard>
</DataTrigger.EnterActions>
</DataTrigger>
</Style.Triggers>
</Style>
</Border.Style>
<TextBlock/>
</Border>

Button Template - IsMouseOver stops working after IsPressed is executed

I have a strange problem and I hope you can help me.
I created a style for a button and added some triggers to the template.
One for IsMouseOver and one for IsPressed.
Both triggers have an EnterAction and an ExitAction animating the background-color of the template.
When I just hover over the button I can see the color changing, but after I clicked on the button the hover trigger stops working.
Here's a example code:
<Button Margin="142,130,214,138" Content="Hi Mum!">
<Button.Resources>
<Color x:Key="backgroundColor" A="255" R="52" G="152" B="219" />
<Color x:Key="hoverBackgroundColor" A="255" R="62" G="182" B="255" />
<Color x:Key="pressedBackgroundColor" A="255" R="42" G="122" B="175" />
</Button.Resources>
<Button.Style>
<Style TargetType="{x:Type Button}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type Button}">
<Border BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
CornerRadius="6">
<Border.Background>
<SolidColorBrush x:Name="backgroundBrush" Color="{StaticResource backgroundColor}" />
</Border.Background>
<ContentPresenter ContentTemplate="{TemplateBinding ContentTemplate}"
Content="{TemplateBinding Content}"
ContentStringFormat="{TemplateBinding ContentStringFormat}"
Focusable="False"
HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
Margin="{TemplateBinding Padding}"
RecognizesAccessKey="True"
SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}"
VerticalAlignment="{TemplateBinding VerticalContentAlignment}" />
</Border>
<ControlTemplate.Triggers>
<Trigger Property="IsMouseOver" Value="True">
<Trigger.EnterActions>
<BeginStoryboard>
<Storyboard>
<ColorAnimation Storyboard.TargetName="backgroundBrush" Storyboard.TargetProperty="Color" To="{StaticResource hoverBackgroundColor}" Duration="0:0:0.2" />
</Storyboard>
</BeginStoryboard>
</Trigger.EnterActions>
<Trigger.ExitActions>
<BeginStoryboard>
<Storyboard>
<ColorAnimation Storyboard.TargetName="backgroundBrush" Storyboard.TargetProperty="Color" To="{StaticResource backgroundColor}" Duration="0:0:0.2" />
</Storyboard>
</BeginStoryboard>
</Trigger.ExitActions>
</Trigger>
<Trigger Property="IsPressed" Value="True">
<Trigger.EnterActions>
<BeginStoryboard>
<Storyboard>
<ColorAnimation Storyboard.TargetName="backgroundBrush" Storyboard.TargetProperty="Color" To="{StaticResource pressedBackgroundColor}" Duration="0:0:0.2" />
</Storyboard>
</BeginStoryboard>
</Trigger.EnterActions>
<Trigger.ExitActions>
<BeginStoryboard>
<Storyboard>
<ColorAnimation Storyboard.TargetName="backgroundBrush" Storyboard.TargetProperty="Color" To="{StaticResource backgroundColor}" Duration="0:0:0.2" />
</Storyboard>
</BeginStoryboard>
</Trigger.ExitActions>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</Button.Style>
</Button>
Looks like last trigger wins (try changing the order of your triggers, IsPressed first and IsMouseOver second and you'll see).
You really should use the VisualStateManager for this kind of stuff.
See the default's button template at the msdn for how to use the VSM.
http://msdn.microsoft.com/en-us/library/cc278069(v=vs.95).aspx
Edit for Sheridan : it works like a charm :
<Window.Resources>
<Color x:Key="OverColor">Blue</Color>
<Color x:Key="PressedColor">Green</Color>
</Window.Resources>
<Grid>
<Button Content="Hi sheridan!" HorizontalAlignment="Center" VerticalAlignment="Center">
<Button.Style>
<Style TargetType="{x:Type Button}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type Button}">
<Border Background="LightBlue">
<VisualStateManager.VisualStateGroups>
<VisualStateGroup x:Name="CommonStates">
<VisualStateGroup.Transitions>
<VisualTransition GeneratedDuration="0:0:0.2"/>
</VisualStateGroup.Transitions>
<VisualState x:Name="Normal"/>
<VisualState x:Name="Pressed">
<Storyboard>
<ColorAnimation Storyboard.TargetProperty="(Background).(SolidColorBrush.Color)"
To="{StaticResource PressedColor}"/>
</Storyboard>
</VisualState>
<VisualState x:Name="MouseOver">
<Storyboard>
<ColorAnimation Storyboard.TargetProperty="(Background).(SolidColorBrush.Color)"
To="{StaticResource OverColor}"/>
</Storyboard>
</VisualState>
</VisualStateGroup>
</VisualStateManager.VisualStateGroups>
<ContentPresenter Content="{TemplateBinding Content}"/>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</Button.Style>
</Button>
</Grid>
There are three parts to this solution:
Name your IsMouseOver BeginStoryBoard objects.
Use those names in two StopStoryBoard objects in the IsPressed Trigger.EnterActions.
Reverse the order of your Trigger objects:
You should end up with something like this:
<Trigger Property="IsPressed" Value="True">
<Trigger.EnterActions>
<StopStoryboard BeginStoryboardName="MouseOverStoryBoard" />
<StopStoryboard BeginStoryboardName="MouseOverStoryBoard2" />
<BeginStoryboard>
<Storyboard>
<ColorAnimation Storyboard.TargetName="backgroundBrush" Storyboard.TargetProperty="Color" To="{StaticResource pressedBackgroundColor}" Duration="0:0:0.2" />
</Storyboard>
</BeginStoryboard>
</Trigger.EnterActions>
<Trigger.ExitActions>
<BeginStoryboard>
<Storyboard>
<ColorAnimation Storyboard.TargetName="backgroundBrush" Storyboard.TargetProperty="Color" To="{StaticResource backgroundColor}" Duration="0:0:0.2" />
</Storyboard>
</BeginStoryboard>
</Trigger.ExitActions>
</Trigger>
<Trigger Property="IsMouseOver" Value="True">
<Trigger.EnterActions>
<BeginStoryboard Name="MouseOverStoryBoard">
<Storyboard>
<ColorAnimation Storyboard.TargetName="backgroundBrush" Storyboard.TargetProperty="Color" To="{StaticResource hoverBackgroundColor}" Duration="0:0:0.2" />
</Storyboard>
</BeginStoryboard>
</Trigger.EnterActions>
<Trigger.ExitActions>
<BeginStoryboard Name="MouseOverStoryBoard2">
<Storyboard>
<ColorAnimation Storyboard.TargetName="backgroundBrush" Storyboard.TargetProperty="Color" To="{StaticResource backgroundColor}" Duration="0:0:0.2" />
</Storyboard>
</BeginStoryboard>
</Trigger.ExitActions>
</Trigger>
Actually, I think that you might be able to do without the second StopStoryboard, but having them both won't hurt.

How to view border/popup for 5 seconds?

I want to animate a border like popup which will be visible for 5 seconds then collapse. When the border is visible, it will be only visible for 5 seconds and then collapse. This will be repeated everytime the border is visible. I have tried but it only appearing once. Can someone please explain to me the mistake in which I have made?
Here is the Style that i have implemented
<Grid.Resources>
<Style x:Key="NotificationStyle" TargetType="{x:Type Border}">
<Style.Triggers>
<Trigger Property="Visibility" Value="Visible">
<Trigger.EnterActions>
<BeginStoryboard x:Name="NotificationStoryBoard">
<Storyboard >
<ObjectAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetProperty="(UIElement.Visibility)">
<DiscreteObjectKeyFrame KeyTime="00:00:00" Value="{x:Static Visibility.Visible}"/>
<DiscreteObjectKeyFrame KeyTime="00:00:05" Value="{x:Static Visibility.Collapsed}"/>
</ObjectAnimationUsingKeyFrames>
</Storyboard>
</BeginStoryboard>
</Trigger.EnterActions>
</Trigger>
</Style.Triggers>
</Style>
</Grid.Resources>
Here is border...
<Border Name="NotifciationPopUp" Background="White" Height="80" Width="200" BorderBrush="Gray" BorderThickness="1" VerticalAlignment="Bottom" HorizontalAlignment="Left" Visibility="Collapsed" Margin="10,0,0,10" Style="{StaticResource NotificationStyle}">
I realized hides the border in such a way:
Style:
<Style x:Key="NotificationStyle" TargetType="{x:Type Border}">
<Style.Triggers>
<Trigger Property="Visibility" Value="Visible">
<Trigger.EnterActions>
<BeginStoryboard>
<Storyboard>
<DoubleAnimation Storyboard.TargetProperty="Opacity" BeginTime="0:0:0" From="0.0" To="1.0" Duration="0:0:1.0" />
<DoubleAnimation Storyboard.TargetProperty="Opacity" BeginTime="0:0:5" From="1.0" To="0.0" Duration="0:0:1.0" />
</Storyboard>
</BeginStoryboard>
</Trigger.EnterActions>
</Trigger>
</Style.Triggers>
</Style>
Grid:
<Grid>
<Border Name="MyBorder" Width="100" Visibility="Hidden" Height="50" BorderThickness="2" BorderBrush="OrangeRed" Style="{StaticResource NotificationStyle}">
<TextBlock Text="Some information" TextAlignment="Center" VerticalAlignment="Center" />
</Border>
<ToggleButton Name="MyButton" Content="Show border" Width="100" Height="30" VerticalAlignment="Bottom" Click="Button_Click" />
</Grid>
In code:
private void Button_Click(object sender, RoutedEventArgs e)
{
if (MyButton.IsChecked == true)
{
MyBorder.Visibility = System.Windows.Visibility.Visible;
}
if (MyButton.IsChecked == false)
{
MyBorder.Visibility = System.Windows.Visibility.Hidden;
}
}
From his experiments I understood that if the property was once used in animation, then working with it is only possible from the animation-triggers. Accordingly, the access code of the property I have not received.
Besides, then the control's used Visibility=Collapsed, he it does not receive messages from the system and the animation will not work. Although a property "Hidden" should take messages, but I have not worked as well as animation, so in example I used opacity.

Categories