无限动画不会被主页按钮打断

时间:2012-04-21 15:13:51

标签: iphone animation uiview

我有一个uiview子类的几个对象,在viewcontroller的主视图中,我通过在类中调用以下方法来无限制动画:

- (void)hover:(NSNumber *)upDown {
    int sense = [upDown intValue];
    [UIView animateWithDuration:0.8 delay:0.1 options:UIViewAnimationOptionCurveEaseInOut | UIViewAnimationOptionAllowUserInteraction
                     animations:^{                        
                         CGRect frame = self.frame;
                         frame.origin.y += (sense==1?1:-1) * 5;
                         self.frame = frame;
                     }
                     completion:^(BOOL finished){ 
                         [self hover:[NSNumber numberWithInt:(sense==1?0:1)]];
                     }];             
}

除了在设备中,当按下主页按钮时,应用程序半冻结(应用程序最终通过反复按住主页按钮一段时间后进入背景)并且与其他按钮的任何交互停止工作。它可以在任何其他情况下正常工作,即只要我不按下主页按钮,我就可以浏览控制器,按下按钮等......并在模拟器上。

有什么想法吗?

更新:罪魁祸首似乎是我正在应用于我正在制作动画的视图的影子

self.layer.shadowColor = [UIColor blackColor].CGColor;
self.layer.shadowOpacity = 1.0;
self.layer.shadowRadius = 5.0;

这似乎导致某种开销只影响应用程序无法进入后台状态???

有人遇到过这个吗?

更新:最后,我决定摆脱该代码,并在drawRect:方法中使用Quartz绘制阴影。我怀疑这个问题可能与iPhone在进入后台模式之前拍摄的快照以及应用于边界外的图层的阴影有关,但这只是猜测。

3 个答案:

答案 0 :(得分:2)

基本上问题与获得圆形和阴影的方式有关:

[self.layer setCornerRadius:radius];

self.layer.shadowColor = [UIColor blackColor].CGColor;
self.layer.shadowOpacity = 0.2;
self.layer.shadowRadius = 5;
self.layer.shadowOffset = CGSizeMake(0, 10);

阴影在视图框架之外绘制,而iPhone进入背景状态的过程在动画制作时似乎并不喜欢。

正如我在更新中提到的,我摆脱了这个并使用Quartz在框架内绘制两个形状的阴影。关于如何做到这一点有很多帖子,但无论如何它仍然存在:

-(void)drawRect:(CGRect)rect
{
   const CGFloat *cComps = CGColorGetComponents([UIColor blackColor]).CGColor;
   CGContextRef context = UIGraphicsGetCurrentContext();

   CGFloat center = rect.size.width / 2.0;
   CGFloat radius = center;

   CGContextBeginPath(context);
   CGContextSetShadowWithColor(context, CGSizeMake(0, 10), 4, [UIColor colorWithWhite:0     alpha:0.1].CGColor);
   CGContextAddArc(context, center, center, radius, 0, 2*M_PI, 1);
   CGContextSetRGBFillColor(context, cComps[0], cComps[1], cComps[2], 1.0);
   CGContextFillPath(context);
}

注意:我将视图的高度设置为+ 15px以容纳底部的阴影。

希望它有所帮助。它肯定让我生气了几天......

答案 1 :(得分:1)

我最近遇到了这个问题,这篇文章非常有助于识别罪魁祸首。事实证明,简单地在阴影层上设置shouldRasterize就足以防止冻结。 (您还应将rasterizationScale设置为与设备的主屏幕比例相同。)

我所有的阴影图层都是相对静态的,并没有经常动画,所以YMMV。

您的标准阴影添加代码:

layer.shadowColor = [UIColor blackColor].CGColor;
layer.shadowOffset = CGSizeMake(0, 1);
layer.shadowOpacity = 0.5;
layer.shadowRadius = 1.0;

这是您需要添加的内容:

layer.rasterizationScale = [[UIScreen mainScreen] scale];
layer.shouldRasterize = YES;

答案 2 :(得分:0)

我的第一个想法是你应该在你的.h文件中实现一个BOOL(我们称之为stopGoing)。然后执行以下操作:

- (void)hover:(NSNumber *)upDown {
    if(!stopGoing){
        int sense = [upDown intValue];
        [UIView animateWithDuration:0.8 delay:0.1 options:UIViewAnimationOptionCurveEaseInOut | UIViewAnimationOptionAllowUserInteraction
                     animations:^{                        
                         CGRect frame = self.frame;
                         frame.origin.y += (sense==1?1:-1) * 5;
                         self.frame = frame;
                     }
                     completion:^(BOOL finished){ 
                         [self hover:[NSNumber numberWithInt:(sense==1?0:1)]];
                     }];
    }  else {
        // do something else
    }           
}

然后,在你已经链接到按钮的IBAction中,只需这样做:

-(IBAction)myButton:(id)sender{
    stopGoing = YES;
}

这应该有效地阻止循环,而不是太过侵入。