如何依次链接不同层的核心动画? [英] How can I chain Core Animations for different Layers one after the other?
问题描述
我有一个启用了页面调度的scrollView和N个页面,它们是UIViews作为scrollView的子视图。
我正在尝试执行以下操作:
用户滚动到第n页。
此时,先前添加到页面编号n
(即,页面[[scrollView子视图] objectAtIndex:n-1] .layer subLayers])中的7个CALayer淡入,在其他。
但是我不知道如何依次使CALayers淡入。到目前为止,我已经尝试了以下3种方法来实现我的控制器的委托方法: b $ b(假设我对图层有一个数组,并且在创建时将其不透明度设置为0)
-(无效)scrollViewDidEndDecelerating:(UIScrollView *)scrollView
{
int pageNumber = floor(self.scrollView.contentOffset.x / self.scrollView.frame.size.width);
if(pageNumber ==(n-1))
{
int timeOffset = 0;
[CATransaction开始];
for(CALayer * layerArray的图层)
{
CABasicAnimation * a = [CABasicAnimation animationWithKeyPath:@ opacity];
a.duration = 6;
a.beginTime = timeOffset ++;
a.fromValue = [NSNumber numberWithFloat:0。];
a.toValue = [NSNumber numberWithFloat:1。];
[layer addAnimation:a forKey:nil];
}
[CATransaction commit];
}
}
-(void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView
{
int pageNumber = floor(self.scrollView.contentOffset.x / self.scrollView.frame.size.width);
if(pageNumber ==(n-1))
{
int timeOffset = 0;
[CATransaction开始];
for(CALayer * layerArray的图层)
{
CABasicAnimation * a = [CABasicAnimation animation];
a.duration = 6;
a.beginTime = timeOffset ++;
[layer addAnimation:a forKey:@ opacity];
[layer setOpacity:1];
}
[CATransaction commit];
}
}
-(void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView
{
int pageNumber = floor(self.scrollView .contentOffset.x / self.scrollView.frame.size.width);
if(pageNumber ==(n-1))
{
int timeOffset = 0;
for(CALayer * layerArray中的图层)
{
[CATransaction begin];
CABasicAnimation * a = [CABasicAnimation动画];
a.duration = 6;
a.beginTime = timeOffset ++;
[layer addAnimation:a forKey:@ opacity];
[layer setOpacity:1];
}
for(CALayer * layerArray中的图层)
[CATransaction commit];
}
}
但似乎都不起作用。当用户滚动到正确的页面时,所有层都立即可见,没有太多的褪色,而且绝对没有任何顺序。
有什么想法吗?
实际上,事实证明,关键是根据参考系获取当前时间,并向该当前时间添加任何时间偏移量时间。
例如,这段代码中的某些内容将导致n层(假定存储在某个数组中)依次淡入淡出。
CGFloat timeOffset = 0;
[CATransaction开始];
for(CALayer * layers in layer){
CABasicAnimation * a = [CABasicAnimation animationWithKeyPath:@ opacity];
a.fromValue = @(0);
a.toValue = @(1);
a.fillMode = kCAFillModeForwards;
a.beginTime = [layerLayerTime:CACurrentMediaTime()fromLayer:nil] + timeOffset;
a.duration = 0.8;
a.removedOnCompletion =否;
[layer addAnimation:a forKey:nil];
timeOffset + = a.duration;
}
[CATransaction commit];
在上述情况下,参照系只是调用发生的当前时间。 / p>
I have a scrollView with paging enabled and a number N of pages, which are UIViews as subviews of the scrollView.
I'm trying to do the following:
User scrolls to page number n. At that point, 7 CALayers which were previously added to page number n (that is, to page [[scrollView subviews] objectAtIndex:n-1].layer subLayers]) fade in, one after the other.
But I can't figure out how to make the CALayers fadeIn sequentially.So far, I've tried the following 3 approaches from my controller's delegate method: (assume I have an array to the layers and that their opacity was set to 0 upon creation)
- (void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView
{
int pageNumber = floor(self.scrollView.contentOffset.x / self.scrollView.frame.size.width);
if(pageNumber == (n-1))
{
int timeOffset = 0;
[CATransaction begin];
for(CALayer *layer in layerArray)
{
CABasicAnimation *a = [CABasicAnimation animationWithKeyPath:@"opacity"];
a.duration = 6;
a.beginTime = timeOffset++;
a.fromValue = [NSNumber numberWithFloat:0.];
a.toValue = [NSNumber numberWithFloat:1.];
[layer addAnimation:a forKey:nil];
}
[CATransaction commit];
}
}
- (void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView
{
int pageNumber = floor(self.scrollView.contentOffset.x / self.scrollView.frame.size.width);
if(pageNumber == (n-1))
{
int timeOffset = 0;
[CATransaction begin];
for(CALayer *layer in layerArray)
{
CABasicAnimation *a = [CABasicAnimation animation];
a.duration = 6;
a.beginTime = timeOffset++;
[layer addAnimation:a forKey:@"opacity"];
[layer setOpacity:1];
}
[CATransaction commit];
}
}
- (void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView
{
int pageNumber = floor(self.scrollView.contentOffset.x / self.scrollView.frame.size.width);
if(pageNumber == (n-1))
{
int timeOffset = 0;
for(CALayer *layer in layerArray)
{
[CATransaction begin];
CABasicAnimation *a = [CABasicAnimation animation];
a.duration = 6;
a.beginTime = timeOffset++;
[layer addAnimation:a forKey:@"opacity"];
[layer setOpacity:1];
}
for(CALayer *layer in layerArray)
[CATransaction commit];
}
}
But neither seems to work. When the user scrolls to the right page, all layers become visible at once, without much of a fade and definitely not in any sequential order.
Any ideas?
Actually, it turns out that the key is getting the current time in terms of a frame of reference and adding any time offset to that current time. This works also for non-grouped animations.
For instance, something along the lines of this code would cause n layers (assumed to be stored in some array) to sequentially fade in one after the other, each taking .8 secs.:
CGFloat timeOffset = 0;
[CATransaction begin];
for (CALayer *layer in layers) {
CABasicAnimation *a = [CABasicAnimation animationWithKeyPath:@"opacity"];
a.fromValue = @(0);
a.toValue = @(1);
a.fillMode = kCAFillModeForwards;
a.beginTime = [layer convertTime:CACurrentMediaTime() fromLayer:nil] + timeOffset;
a.duration = 0.8;
a.removedOnCompletion = NO;
[layer addAnimation:a forKey:nil];
timeOffset += a.duration;
}
[CATransaction commit];
In the above case, the frame of reference is simply the current time when the invocations take place.
这篇关于如何依次链接不同层的核心动画?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!