Question

I'm working in MonoMac and am attempting to animate the width and height constraint for a control dynamically on a button click. After reading the following pages, I'm assuming that I have to use the Animator proxy of my constraint. However, the following code doesn't seem to get the job done.

NSLayoutConstraint.constant ignoring animation http://cocoa-mono.org/archives/235/using-animator-with-frameorigin/

Code:

// makes sure we animate from 0 to calculated width
double newWidth = ...
widthConstraint.Constant = 0;

var animation = new NSAnimation() { Duration = 0.5, AnimationCurve = NSAnimationCurve.EaseInOut };
widthConstraint.Animations = new NSDictionary("constant", animation);
((NSLayoutConstraint)widthConstraint.Animator).Constant = newWidth;

The result of this is the control has a width of newWidth but it is not animated--it changes immediately.

Was it helpful?

Solution 2

Turns out I was using the wrong type of animation. The following code works:

// makes sure we animate from 0 to calculated width
float newWidth, newHeight = ...
widthConstraint.Constant = 0;
heightConstraint.Constant = 30;

var widthAnimation = new CABasicAnimation();
widthAnimation .TimingFunction = CAMediaTimingFunction.FromName(CAMediaTimingFunction.EaseInEaseOut);
widthAnimation .Duration = 0.25;

var heightAnimation = new CABasicAnimation();
widthAnimation .TimingFunction = CAMediaTimingFunction.FromName(CAMediaTimingFunction.EaseInEaseOut);
widthAnimation .Duration = 0.25;

widthConstraint.Animations = new NSDictionary("constant", widthAnimation);
heightConstraint.Animations = new NSDictionary("constant", heightAnimation);

NSAnimationContext.BeginGrouping();
NSAnimationContext.CurrentContext.Duration = widthAnimation.Duration;
NSAnimationContext.CurrentContext.CompletionHandler = new NSAction(() => ((NSLayoutConstraint)heightConstraint.Animator).Constant = newHeight);
((NSLayoutConstraint)widthConstraint.Animator).Constant = newWidth;
NSAnimationContext.EndGrouping();

This runs the width animation and then the height animation.

OTHER TIPS

You have to actually 'run' the animation. Do it like this:

float newWidth = 300;
NSAnimationContext.RunAnimation((ctx) => { 
    ctx.Duration = 0.5;
    ctx.TimingFunction = CAMediaTimingFunction.FromName(CAMediaTimingFunction.EaseInEaseOut);
    ((NSLayoutConstraint)widthConstraint.Animator).Constant = newWidth;
}, () => { 
    Console.WriteLine("Animation Complete"); 
});
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top