slider value to change the duration of spin using DoubleAnimation class - c#

I am trying to do a basic animation using the DoubleAnimation class in WPF. On a button click the rectangle spins. The cs code is
DoubleAnimation da = new DoubleAnimation();
da.From = 0; // start from 0 to 360, full circle
da.To = 360;
da.Duration = new Duration(TimeSpan.FromSeconds(0.5));
da.RepeatBehavior = RepeatBehavior.Forever;
RotateTransform rt = new RotateTransform();
rectangle1.RenderTransform = rt;
rt.BeginAnimation(RotateTransform.AngleProperty, da);
What i am trying to do is to update the da.Duration = new Duration(TimeSpan.FromSeconds(0.5)) value with the slider value.
Tried with slider value binding, but not able to get this correctly.

Changing the Duration is not enough. How fast the animation is controlled by the inner AnimationClock. This clock is initialized just once after you call BeginAnimation(). So you have to update the inner AnimationClock by using ApplyAnimationClock() method.
Also note that you should also set the From property to the currently animated value, so that when changing the Slider's Value, the Angle will be animated smoothly (without restarting from 0):
//The ValueChanged handler for your Slider
private void slider_ValueChanged(object sender,
RoutedPropertyChangedEventArgs e){
da.Duration = new Duration(TimeSpan.FromMilliseconds(yourSlider.Value));
da.From = rt.Angle;
rt.ApplyAnimationClock(RotateTransform.AngleProperty, da.CreateClock());
}
Note that I suppose the slider's Value corresponds to the number of milliseconds, so the Maximum value of the Slider should be large enough (about several thousands) if you don't want your Rectangle to be rotated super fast. Also all the variables you declared should be able to access inside the ValueChanged handler.
One more important note is you should use By property here instead of To, like this:
da.By = 360;
That way you can just update the From without caring about the To (it is always 360 degrees rotated).

Related

How to reverse or repeat RotateTransform?

I followed a tutorial on rotating a picture bound to a button and it should be pretty simple, yet I can't figure it out.
private void rotateMenu()
{
int rotateAngle;
if (menuState) rotateAngle = -90;
else rotateAngle = 90;
DoubleAnimation myanimation = new DoubleAnimation(0, rotateAngle, new Duration(TimeSpan.FromMilliseconds(222)));
var rotateTransform = new RotateTransform(rotateAngle, 24.5, 24.5);
menuButtonImage.RenderTransform = rotateTransform;
rotateTransform.BeginAnimation(RotateTransform.AngleProperty, myanimation);
}
First button press - rotate the picture by 90 degrees. Simple, works.
Now I want to either reverse the rotation or rotate another 90 degrees.
Animation works fine but the outcome always switches back to the picture being rotated 90 degrees, no matter what I set the second rotateAngle to.
Basically what I get is in the first part of the picture, want I need in the second part.
What am I doing wrong here? Why can't I rotate the picture again? I tried with -90, 90 and lots of other values, e.g. 45 degrees, yet no rotation happening?
That's because the picture isn't actually rotated, but it's only rendered rotated. Until the rendertransform gets a new transform, it will stay rotated.
This will rotate it back, So you could try:
DoubleAnimation myanimation2 =
new DoubleAnimation(0, new Duration(TimeSpan.FromMilliseconds(222)));
only use the toValue parameter overload to rotate it back.
I would make something like:
// initial angle is 0
RotateTransform _rotateTransform = new RotateTransform(0.0, 24.5, 24.5);
Duration _rotationSpeed;
private void CreateRotation()
{
_rotationSpeed = new Duration(TimeSpan.FromMilliseconds(222));
menuButtonImage.RenderTransform = _rotateTransform;
}
private void rotateToSide()
{
DoubleAnimation myanimation = new DoubleAnimation(90, _rotationSpeed);
_rotateTransform.BeginAnimation(RotateTransform.AngleProperty, myanimation);
}
private void rotateToDefault()
{
DoubleAnimation myanimation = new DoubleAnimation(0, _rotationSpeed);
_rotateTransform.BeginAnimation(RotateTransform.AngleProperty, myanimation);
}
For your information (as I can read from your code) You don't have to change the Angle property of the rotateTransform object. The rotateTransform.BeginAnimation will alter the property.

How to animate using Path with Storyboard in C#

So, I am trying to move my rectangular boxes around a grid like this -
For this, I am using a Story board.
I am using DoubleAnimation to move the boxes on X-Axis and Y-Axis in one of my Class. I am calling this class from MainWindow class. But, for every box, and for every turn, I have to create a new Double animation, assign the offset values, the start time, the duration etc. like this -
//Code to move Boxes 1-4 to first grid point in their path
TranslateTransform moveTransform = new TranslateTransform();
moveTransform.X = 0;
moveTransform.Y = 0;
x.RenderTransform = moveTransform;
Storyboard s = new Storyboard();
DoubleAnimation Move1= new DoubleAnimation();
Move1.From = 0;
Move1.To = xPosition; // calculate correct offset here
Move1.Duration = new Duration(TimeSpan.FromSeconds(hops));
if (x==Box2)
{
Move1.BeginTime = TimeSpan.FromSeconds(5);//For Box 2, the first move will be across Y-Axis and hence X-Axis move will be delayed by 5 seconds.
}
else
{
Move1.BeginTime = TimeSpan.Zero;
}
Storyboard.SetTarget(Move1, x);
Storyboard.SetTargetProperty(Move1, new PropertyPath("(UIElement.RenderTransform).(X)"));
s.Children.Add(Move1);
I know there is a way to define the path to reach the destination from source, but I am not sure how to do it? Also, I am not sure if what I am doing here is the optimal way.
So, my question is -
What is the better way to do this? How can we define paths for animation?
I am a newbie to C# so please do not mind if this sounds silly.
Thank you!
I was able to do it without using path.
For every move, I created a new double animation.
So for Left - Down - Right movement, I created 3 double animations with
X-Axis, Y-Axis and X-Axis again.

Windows Phone Resize an Image with a Storyboard

I simply have an Image, and I set its width and height by assigning some numbers. For example, First Height and Width: 400 x 800. Second Height and Width: 200 x 400.
So if you do such a mainstreamed thing, there won't be any transition when resizing it, it just gets smaller immediately in a blink of eye. But I want it to resize between those "specific" measurements by transition (or animating) in 1 or 2 seconds.
I know Microsoft Expression Blend do some storyboards, but I could not do this by data binding. I databinded this image with a value, when the value changes, image resizes also. But I could not record any storyboard to create a transition.
What do you suggest me to do?
Thanks
I think something along the lines of this might work...
private void buttonStart_Click(object sender, RoutedEventArgs e)
{
CreateAnimation(400, 200).Begin();
}
private Storyboard CreateAnimation(double from, double to)
{
Storyboard sb = new Storyboard();
DoubleAnimation Animation = new DoubleAnimation();
Animation.From = from;
Animation.To = to;
Animation.Duration = new Duration(TimeSpan.FromSeconds(1.0));
Storyboard.SetTarget(Animation, ITEMNAME);
Storyboard.SetTargetProperty(Animation, new PropertyPath("(Width)"));
sb.Children.Add(Animation);
return sb;
}
Just create two double animations for the height and width to use simultaneously.

WPF TranslateTransform

Im trying to use the TranslateTransform class to move a image on a Grid on Y axis. I need this movment to be smooth so i can not use SetMargin or SetCanvas. I try this in code behind:
public void MoveTo(Image target, double oldY, double newY)
{
var trans = new TranslateTransform();
var anim2 = new DoubleAnimation(0, newY, TimeSpan.FromSeconds(2))
{EasingFunction = new SineEase()};
target.RenderTransform = trans;
trans.BeginAnimation(TranslateTransform.YProperty, anim2);
}
The object i want to use (a Image control) is placed on a Grid.
For the first time everything works fine.
The problems comes when i try to move the object again using the same function.
The object (a Image control) first move to the start position (initial Y coordinate) then the animation begins.
Is it not suposed for the TranslateTransform to change the coordinates (in my case the Margin property) too?
Thank you.
The transform does not change the original values.they are your point of origin. If you want a new point of origin each time you move you can handle the animation completed event. Or from your transform you can get your current offset and make that your new start point for the animation.
In other words your start values would always be your last move to values
The TranslateTransform is a specific kind of render transformation. Rather that changing properties of the control (such as the Margin property), it simply affects how the control is displayed on the screen.
You have to use the By property of DoubleAnimation.
Try that:
//everytime you execute this anmation your object will be moved 2.0 further
double offset = 2.0
var anim2 = new DoubleAnimation(newY, TimeSpan.FromSeconds(2));
anim2.To = null;
anim2.By = offset;
You've explicitly told the animation to start from 0. It's doing what you've told it.
Just remove the explicit zero fromvalue and everything will work.
var anim2 = new DoubleAnimation(newY, TimeSpan.FromSeconds(2))
{ EasingFunction = new SineEase() };

Not being able to animate TranslateTransform.XProperty with code

I have a method that enables me to animate objects that have to do with a DoubleAnimation:
public void animDouble(DependencyObject target, DependencyProperty property, double to, TimeSpan duration, double? from = null, TimeSpan? beginTime = null, IEasingFunction e = null)
{
DoubleAnimation animation = new DoubleAnimation();
animation.To = to;
if (beginTime == null)
beginTime = TimeSpan.FromSeconds(0);
if (from != null)
animation.From = from;
animation.BeginTime = beginTime;
animation.Duration = duration;
if (e != null)
animation.EasingFunction = e;
//start animating
Storyboard.SetTarget(animation, target); // what object will be animated?
Storyboard.SetTargetProperty(animation, new PropertyPath(property)); // what property will be animated
Storyboard sb = new Storyboard();
sb.Children.Add(animation);
sb.Begin();
}
so if I have a boarder called br1 for example and I want to animate it's height I will call the method as:
animDouble(br1, FrameworkElement.HeightProperty, 150, TimeSpan.FromSeconds(5));
if I want to animate it's width I will do:
animDouble(br1, FrameworkElement.WidthProperty, 150, TimeSpan.FromSeconds(5));
I could also animate it's visibility with the same method.
for some reason I am not able to animate its x property in order to translate it along the x axis or y-axis. When I call the method as:
a.animDouble(br1, TranslateTransform.XProperty, 150, TimeSpan.FromSeconds(5));
the boarder does not animates. I don't get any errors aether.
Somehow i would have expected an error, well, anyway, the Border owns no such property, if you want to move your control you need to set the RenderTransform or LayoutTransform of the border to a TranslateTransform, then you can pass the transform itself into the method as target.
(The whole storyboard is awfully redundant as you only have one animation, you can just call BeginAnimation on the target itself)
It had to do with registering the name. I found a link in here
I don't know what the method registerName does but I guess I needed it. from the page I managed to get the basic animations. I where not able to animate two things at once SOMETIMES. if you are interested in seeing the method take a look tat this question. I think it is a prety nice class that will enable to create animations with code. copy the namespace to visual studio and copy the first example that I posted so that you can see how it works.

Categories

Resources