I'm new at Silverlight and trying samples for things animating the opacity of an object programatically.
I've come up with the following code:
MapShape myTestShape= RadMapInformationLayer.Items[0] as MapShape;
SolidColorBrush brush = new SolidColorBrush();
brush.Color = Colors.Purple;
myTestShape.Fill = brush;
//create a duration object
Duration duration = new Duration(TimeSpan.FromSeconds(5));
//create the storyboard
Storyboard story = new Storyboard();
//create double animation
DoubleAnimation animation = new DoubleAnimation();
//set the duration property
animation.Duration = duration;
//set the from and too values
animation.From = 1.0;
animation.To = 0.0;
//add the duration to the storyboard
story.Duration = duration;
//now set the target of the animation
Storyboard.SetTarget(animation, myTestShape);
//set the target property of this object
Storyboard.SetTargetProperty(animation, new PropertyPath(UIElement.OpacityProperty));
//add the double animations to the story board
story.Children.Add(animation);
if (!LayoutRoot.Resources.Contains("story1"))
LayoutRoot.Resources.Add("story1", story);
story.Begin();
For the property path I've also tried:
1. new PropertyPath("(FrameworkElement.Opacity)")
2. new PropertyPath("(FrameworkElement.Opacity)")
3. new PropertyPath("(Control.Opacity)")
And a few others, I'm having zero luck with this.
Can anyone see where I'm going wrong?
Thanks,
Jacques
I have done databinding to MapShape.FillProperty before.
Try:
//create double animation
ColorAnimation animation = new ColorAnimation();
//set the duration property
animation.Duration = duration;
//set the from and too values
animation.From = Colors.Purple;
animation.To = Colors.Transparent;
//add the duration to the storyboard
story.Duration = duration;
//now set the target of the animation
Storyboard.SetTarget(animation, rect);
//set the target property of this object
Storyboard.SetTargetProperty(animation, new PropertyPath("(MapShape.Fill).Color"));
EDIT:
As for why your code is not working -- Looking through MapShape.SetShapeFillStroke(), it appears that Telerik won't bind the MapShape's Opacity to its inner primitive shape's Opacity unless you provide a fill. Do you have a Fill defined in XAML? If not, try providing one. Otherwise, maybe the code is defined too early in the Shape's lifecycle (in or after ReadCompleted)?
<telerik:InformationLayer x:Name="StateLayer">
<telerik:InformationLayer.Reader>
...
</telerik:InformationLayer.Reader>
<telerik:InformationLayer.ShapeFill>
<telerik:MapShapeFill Fill="{StaticResource CommonBackgroundLightBrush}" Stroke="#5A636B" StrokeThickness="1" />
</telerik:InformationLayer.ShapeFill>
Related
I am having some trouble animating the items in my ListBox. Animations on the OpacityProperty work great but when i try to animate the position of my ListBoxItem it simply does not move an inch (No exceptions are thrown, not even a log message indicating error).
Here is the code i am using:
private void deletAnimation()
{
Todo todoToDelete = App.ViewModel.Todos[1];
Storyboard storyboard = new Storyboard();
DoubleAnimation alphaAnim = new DoubleAnimation();
alphaAnim.From = 1;
alphaAnim.To = 0;
alphaAnim.Duration = new Duration(TimeSpan.FromMilliseconds(500));
ListBoxItem target = TodoList.ItemContainerGenerator.ContainerFromItem(todoToDelete) as ListBoxItem;
Storyboard.SetTarget(alphaAnim, target);
Storyboard.SetTargetProperty(alphaAnim, new PropertyPath(UIElement.OpacityProperty));
storyboard.Children.Add(alphaAnim);
for (int i = App.ViewModel.Todos.IndexOf(todoToDelete) + 1; i < App.ViewModel.Todos.Count; i++)
{
Todo todo = App.ViewModel.Todos[i];
target = TodoList.ItemContainerGenerator.ContainerFromItem(todo) as ListBoxItem;
DoubleAnimation translateAnim = new DoubleAnimation();
translateAnim.From = target.RenderTransformOrigin.Y;
translateAnim.To = target.RenderTransformOrigin.Y - target.ActualHeight;
translateAnim.Duration = new Duration(TimeSpan.FromMilliseconds(500));
translateAnim.BeginTime = TimeSpan.FromMilliseconds(500);
Storyboard.SetTarget(translateAnim, target);
Storyboard.SetTargetProperty(translateAnim, new PropertyPath(TranslateTransform.YProperty));
storyboard.Children.Add(translateAnim);
}
storyboard.Begin();
}
Some things i have noticed while debugging:
The RenderTransformOrigin.Y property is always 0 no matter which ListBoxItem is referenced.
The Height property is NaN though the ActualHeight property is 67
The parent property of the ListBoxItem is null
These two things make me wonder if i am given a reference to a ListBoxItem that is not rendered of the screen? But as the Opacity animation works perfectly and all of my list is visible(only contains 3 items at the moment) i do not see how this could be the case.
I have also tried using a PointAnimation and animating the RenderTransformOrigin property directly but this gave the same result (nothing that is).
Any help is appreciated, thanks!
Please check out this link:
http://blogs.msdn.com/b/jasongin/archive/2011/01/03/wp7-reorderlistbox-improvements-rearrange-animations-and-more.aspx
Someone has created a class that you can easily incorporate into your app. This has animations for adding/removing items from your list.
This should save you a lot of time and frustration.
i am trying to rotate an object from code behind. Code below:
Storyboard storyBoard = new Storyboard();
//Transform
RotateTransform rotate = new RotateTransform();
rotate.Angle = 45;
rotate.CenterX = 50;
rotate.CenterY = 20;
RodBorder.RenderTransform = rotate;
DoubleAnimation Anim = new DoubleAnimation();
Anim.Duration = new Duration(TimeSpan.FromMilliseconds(3000));
Anim.SetValue(Storyboard.TargetPropertyProperty, rotate);
Storyboard.SetTargetProperty(Anim, new PropertyPath("RenderTransform.Angle"));
Storyboard.SetTarget(Anim, RodBorder);
storyBoard.Children.Add(Anim);
storyBoard.Begin();
RodBorder is a Border which i want to rotate. The problem here is probably the PropertyPath, because i got an exception there.(System.Windows.PropertyPath cannot be set to type System.Windows.Media.RotateTransform) Any ideas are welcome, thank you for your help.
Try Storyboard.TargetProperty="(UIElement.RenderTransform).(RotateTransform.Rotation)".
You can always verify syntax by building sample animation in Blend.
friends,thank you for your time!
There's a problem in the codes below in WPF.I use a ProgressBar and a Animation which show the progress of value changes.When the Animation finished,I try to reset the value to 0 ,so that the ProgressBar can begin a new Animation from 0 to 100 again.But the result is that I can't set the value to 0,it seems that it would be 100 forever no matter how I tried!!!!!
Could you please give me some ideas,thank you!
pbStatus.Value = 0;//Promblem!! pbStatus is a ProgressBar
Duration dr = new Duration(TimeSpan.FromSeconds(2));
DoubleAnimation da = new DoubleAnimation(100, dr);
pbStatus.IsIndeterminate = false;
pbStatus.Visibility = Visibility.Visible;
pbStatus.BeginAnimation(ProgressBar.ValueProperty, da);
Please see this article.
Summary: There are three ways to set a value after an animation.
Set the animation's FillBehavior property to Stop
Remove the entire Storyboard. (Not applicable since you have no storyboard)
Remove the animation from the individual property.
(1) Set the fill behaviour of the animation to stop:
da.FillBehavior = FillBehavior.Stop;
(3) Remove the animation by calling this before setting the new value:
pbStatus.BeginAnimation(ProgressBar.ValueProperty, null);
From this article:
private void CreateDynamicProgressBarControl()
{
ProgressBar PBar2 = new ProgressBar();
PBar2.IsIndeterminate = false;
PBar2.Orientation = Orientation.Horizontal;
PBar2.Width = 100;
PBar2.Height = 10;
Duration duration = new Duration(TimeSpan.FromSeconds(10));
DoubleAnimation doubleanimation = new DoubleAnimation(100.0, duration);
PBar2.BeginAnimation(ProgressBar.ValueProperty, doubleanimation);
SBar.Items.Add(PBar2);
}
I'm doing a Surface Application.
And there I have something like a bulletin board where little cards with news on it are pinned on.
On click they shall fly out of the board and scale bigger.
My storyboard works well, except for the first time it runs. It's not a smooth animation then but it scales to its final size immediately and it's the same with the orientation-property. Just the center-property seems to behave correctly.
This is an example for one of my Storyboards doing that:
Storyboard stb = new Storyboard();
PointAnimation moveCenter = new PointAnimation();
DoubleAnimationUsingKeyFrames changeWidth = new DoubleAnimationUsingKeyFrames();
DoubleAnimationUsingKeyFrames changeHeight = new DoubleAnimationUsingKeyFrames();
DoubleAnimationUsingKeyFrames changeOrientation = new DoubleAnimationUsingKeyFrames();
moveCenter.From = News1.ActualCenter;
moveCenter.To = new Point(250, 400);
moveCenter.Duration = new Duration(TimeSpan.FromSeconds(1.0));
moveCenter.FillBehavior = FillBehavior.Stop;
stb.Children.Add(moveCenter);
Storyboard.SetTarget(moveCenter, News1);
Storyboard.SetTargetProperty(moveCenter, new PropertyPath(ScatterViewItem.CenterProperty));
changeWidth.Duration = TimeSpan.FromSeconds(1);
changeWidth.KeyFrames.Add(new EasingDoubleKeyFrame(266, KeyTime.FromTimeSpan(new System.TimeSpan(0, 0, 1))));
changeWidth.FillBehavior = FillBehavior.Stop;
stb.Children.Add(changeWidth);
Storyboard.SetTarget(changeWidth, News1);
Storyboard.SetTargetProperty(changeWidth, new PropertyPath(FrameworkElement.WidthProperty));
changeHeight.Duration = TimeSpan.FromSeconds(1);
changeHeight.KeyFrames.Add(new EasingDoubleKeyFrame(400, KeyTime.FromTimeSpan(new System.TimeSpan(0, 0, 1))));
changeHeight.FillBehavior = FillBehavior.Stop;
stb.Children.Add(changeHeight);
Storyboard.SetTarget(changeHeight, News1);
Storyboard.SetTargetProperty(changeHeight, new PropertyPath(FrameworkElement.HeightProperty));
changeOrientation.Duration = TimeSpan.FromSeconds(1);
changeOrientation.KeyFrames.Add(new EasingDoubleKeyFrame(0, KeyTime.FromTimeSpan(new System.TimeSpan(0, 0, 1))));
changeOrientation.FillBehavior = FillBehavior.Stop;
stb.Children.Add(changeOrientation);
Storyboard.SetTarget(changeOrientation, News1);
Storyboard.SetTargetProperty(changeOrientation, new PropertyPath(ScatterViewItem.OrientationProperty));
stb.Begin(this);
News1.Center = new Point(250, 400);
News1.Orientation = 0;
News1.Width = 266;
News1.Height = 400;
Pin1.Visibility = Visibility.Collapsed;
news1IsOutside = true;
Scroll1.IsEnabled = true;
What's wrong with it?
The Problem
The essence of the problem is that you are calling stb.Begin() and then immediately changing News1.Width, etc. Unfortunately stb.Begin() is not guaranteed to start the animations immediately: At times it does so in a dispatcher callback.
What is happening to you is that the first time your storyboard executes, stb.Begin() schedules a dispatcher callback to start the animations and immediately returns. The next four lines of your code update the values:
News1.Center = new Point(250, 400);
News1.Orientation = 0;
News1.Width = 266;
News1.Height = 400;
When the animations actually start in the dispatcher callback they see the new values and use those as their starting values. This causes the object appears to jump to the new value immediately.
For example, changeWidth declares a keyframe that animates the value to 266:
changeWidth.KeyFrames.Add(new EasingDoubleKeyFrame(266, ...
And later the initial width is set to 266:
News1.Width = 266;
So if the storyboard is delayed starting, the width will animate from 266 to 266. In other words, it will not change. If you later use another animation to change News1.Width to something other than 266 and then run the changeWidth animation, it will work.
Your moveCenter animation works reliably because it actually sets its From value to the current value:
moveCenter.From = News1.ActualCenter;
moveCenter.To = new Point(250, 400);
Thus the animation always starts at the old center, even if the News1.Center = new Point(250,400) once the animation has started.
The Solution
Just as you set "From" on your PointAnimation, you can also set an initial value in your other animations. This is done by adding a key frame at time=0 specifying the current width:
changeWidth.Duration = TimeSpan.FromSeconds(1);
changeWidth.KeyFrames.Add(new DiscreteDoubleKeyframe(News1.Width, KeyTime.Paced));
changeWidth.KeyFrames.Add(new EasingDoubleKeyFrame(266, KeyTime.Paced));
This code uses the fact that KeyTime.Paced automatically results in 0% and 100% if there are two key frames. In fact, setting the first frame as KeyFrame.Paced will always be equivalent to KeyTime.FromTimeSpan(TimeSpan.Zero).
Another solution might be to use FillBehavior.HoldEnd, then hook up to the Storyboard.Completed event and:
Set the local values as you originally did
Call Storyboard.Remove
This would also have the advantage that the local values will be accessible from the properties.
My code is here, and I can't edit the offset property of TranslateTransform3D any more after running this:
DoubleAnimation doubleAnimationX =
new DoubleAnimation(x,
new Duration(TimeSpan.FromSeconds(second)));
DoubleAnimation doubleAnimationY =
new DoubleAnimation(y,
new Duration(TimeSpan.FromSeconds(second)));
DoubleAnimation doubleAnimationZ =
new DoubleAnimation(z,
new Duration(TimeSpan.FromSeconds(second)));
translate.BeginAnimation(TranslateTransform3D.OffsetXProperty, doubleAnimationX);
translate.BeginAnimation(TranslateTransform3D.OffsetYProperty, doubleAnimationY);
translate.BeginAnimation(TranslateTransform3D.OffsetZProperty, doubleAnimationZ);
TranslateTransform3D derives from Freezable. Your translate is being frozen after the animation, which makes it immutable.