UIView animateWithDuration不会为cornerRadius变体设置动画

Fra*_*isi 61 cornerradius uiview uiviewanimation

我试图动画的变化cornerRadius一个的UIView实例layer,但的变化cornerRadius立即生效.

这是代码:

UIView *view = [[UIView alloc] initWithFrame:CGRectMake(10, 10, 100, 100)];
view.layer.masksToBounds = YES;
view.layer.cornerRadius = 10.0;
[UIView animateWithDuration:1.0 animations:^{

    [view.layer.cornerRadius = 0.0;

}];
Run Code Online (Sandbox Code Playgroud)

谢谢大家给我任何提示.

编辑:

我设法Core Animation使用a 来动画这个属性CABasicAnimation.

CABasicAnimation *animation = [CABasicAnimation animationWithKeyPath:@"cornerRadius"];
animation.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionLinear];
animation.fromValue = [NSNumber numberWithFloat:10.0f];
animation.toValue = [NSNumber numberWithFloat:0.0f];
animation.duration = 1.0;
[viewToAnimate.layer addAnimation:animation forKey:@"cornerRadius"];
[animation.layer setCornerRadius:0.0];
Run Code Online (Sandbox Code Playgroud)

Dav*_*ist 88

tl; dr:角半径不可动画animateWithDuration:animations:.


文档中有关视图动画的内容.

正如"iOS视图编程指南"中的动画部分所述

UIKit和Core Animation都支持动画,但每种技术提供的支持程度各不相同.在UIKit中,使用UIView对象执行动画

可以使用旧版本设置动画的完整属性列表

[UIView beginAnimations:context:];
[UIView setAnimationDuration:];
// Change properties here...
[UIView commitAnimations];
Run Code Online (Sandbox Code Playgroud)

或者更新的

[UIView animateWithDuration:animations:];
Run Code Online (Sandbox Code Playgroud)

(您正在使用)是:

  • 界限
  • 中央
  • 转换(CGAffineTransform,而不是CATransform3D)
  • α
  • 背景颜色
  • contentStretch

如您所见,cornerRadius不在列表中.

有些困惑

UIView动画实际上仅用于动画视图属性.令人困惑的是,您还可以在UIView动画块内的图层上设置相同属性的动画,即框架,边界,位置,不透明度,backgroundColor.所以人们看到里面的图层动画,animateWithDuration并相信他们可以为那里的任何视图属性设置动画.

同一节继续说:

在您想要执行更复杂的动画或UIView类不支持的动画的地方,您可以使用Core Animation和视图的底层来创建动画.由于视图和图层对象错综复杂地链接在一起,因此对视图图层的更改会影响视图本身.

几行下来你可以阅读核心动画动画属性列表,你会看到这个:

  • 图层的边框(包括图层的边角是否为圆角)

因此,要动画cornerRadius需要使用核心动画,就像你在更新的问题(和答案)中已经说过的那样.我刚补充试图解释为什么会这样.


一些额外的澄清

当人们阅读文档时说这animateWithDuration是推荐的动画制作方法时,很容易相信它正试图取代CABasicAnimation,CAAnimationGroup,CAKeyframeAnimation等,但实际上并非如此.它取代了beginAnimations:context:commitAnimations你上面看到的.

  • 这在 iOS 11 中发生了变化,请参考我的回答 (2认同)

Chi*_*buZ 25

我使用此扩展来设置角半径的变化:

extension UIView
{
    func animateCornerRadius(from: CGFloat, to: CGFloat, duration: CFTimeInterval)
    {
        CATransaction.begin()
        let animation = CABasicAnimation(keyPath: "cornerRadius")
        animation.timingFunction = CAMediaTimingFunction(name: CAMediaTimingFunctionName.linear)
        animation.fromValue = from
        animation.toValue = to
        animation.duration = duration
        CATransaction.setCompletionBlock { [weak self] in
            self?.layer.cornerRadius = to
        }
        layer.add(animation, forKey: "cornerRadius")
        CATransaction.commit()
    }
}
Run Code Online (Sandbox Code Playgroud)

  • 工作得很好.你真的不需要from字段,因为它应该总是`layer.cornerRadius`. (3认同)

Fra*_*isi 15

角半径变化可以是动画的,但唯一的方法是使用CABasicAnimation.希望这有助于那里的人.


aka*_*ity 13

你可以在这里实现UIView动画:http://maniacdev.com/2013/02/ios-uiview-category-allowing-you-to-set-up-customizable-animation-properties

CABasicAnimation *animation = [CABasicAnimation animationWithKeyPath:@"cornerRadius"];
animation.duration = DURATION;
animation.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionLinear];
animation.toValue = @(NEW_CORNER_RADIUS);
animation.fillMode = kCAFillModeForwards;
animation.removedOnCompletion = NO;
[view.layer addAnimation:animation forKey:@"setCornerRadius:"];
Run Code Online (Sandbox Code Playgroud)

  • 由于iOS 11的cornerRadius是可动画的属性 (2认同)

edw*_*dmp 6

iOS 10开始,您实际上可以为cornerRadius设置动画:

UIViewPropertyAnimator(duration: 3.0, curve: .easeIn) {
    square.layer.cornerRadius = 20
}.startAnimation()
Run Code Online (Sandbox Code Playgroud)

  • 可从iOS 10+开始使用。 (2认同)

归档时间:

查看次数:

23613 次

最近记录:

5 年,10 月 前