私はアニメーションの初心者で、数日間 CoreAnimation を試しています。この質問が意味をなさない場合は、遠慮なく警告してください。ただし、次のことを達成しようとしています。私は3つのオブジェクトを持っています:
- 1つは画像であり、特定のパターンに従って移動する必要があります
- 1 つは 2 つの画像を交換する UIImage である必要があります
- 1 つは、内容が変化するテキスト (CATextLayer?) である必要があります。
3 つのアクションは同期して発生する必要があります。
例として、-1 と +1 の間で振動する ECG のような正弦波関数を示すプログラムについて考えてみましょう。最初の画像は、現在の値 (-1、-0.9、-0.8、...) に従って移動します。 0、+0.1、+0.2、... 1)、スワップ画像は正の値の場合は「+」、負の値の場合は「-」を示し、テキストは「正」と「負」の間で交互に表示されます。
CAAnimationGroup を試してみましたが、明らかに何かが欠けています。いくつかのコード:
{
// image that moves
CALayer *img1 = [CALayer layer];
img1.bounds = CGRectMake(0, 0, 20, 20);
img1.position = CGPointMake(x1,y1);
UIImage *img1Image = [UIImage imageNamed:@"image.png"];
img1.contents = (id)img1Image.CGImage;
// image that changes
CALayer *swap = [CALayer layer];
swap.bounds = CGRectMake(0, 0, 30, 30);
swap.position = CGPointMake(x2,y2);
NSString* nameswap = @"img_swap_1.png"
UIImage *swapImg = [UIImage imageNamed:nameswap];
// text
CATextLayer *text = [CATextLayer layer];
text.bounds = CGRectMake(0, 0, 100, 100);
text.position = CGPointMake(x3,y3);
text.string = @"Text";
// create animations
CGFloat duration = 0.2;
CGFloat totalDuration = 0.0;
CGFloat start = 0;
NSMutableArray* animarray = [[NSMutableArray alloc] init];
NSMutableArray* swapanimarray = [[NSMutableArray alloc] init];
NSMutableArray* textanimarray = [[NSMutableArray alloc] init];
float prev_x = 0;
float prev_y = 0;
// I get my values for moving the object
for (NSDictionary* event in self.events) {
float actual_x = [[event valueForKey:@"x"] floatValue];
float actual_y = [[event valueForKey:@"y"] floatValue];
// image move animation
CABasicAnimation *anim = [CABasicAnimation animationWithKeyPath:@"position"];
CGPoint startPt = CGPointMake(prev_x,prev_y);
CGPoint endPt = CGPointMake(actual_x, actual_y);
anim.duration = duration;
anim.fromValue = [NSValue valueWithCGPoint:startPt];
anim.toValue = [NSValue valueWithCGPoint:endPt];
anim.beginTime = start;
anim.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut];
[animarray addObject:anim];
// image swap animation
CABasicAnimation *swapanim = [CABasicAnimation animationWithKeyPath:@"contents"];
swapanim.duration = duration;
swapanim.beginTime = start;
NSString* swapnamefrom = [NSString stringWithFormat:@"%@.png", prev_name];
NSString* swapnameto = [NSString stringWithFormat:@"%@.png", current_name];
UIImage *swapFromImage = [UIImage imageNamed:swapnamefrom];
UIImage *swapToImage = [UIImage imageNamed:swapnameto];
swapanim.fromValue = (id)(swapFromImage.CGImage);
swapanim.toValue = (id)(swapToImage.CGImage);
swapanim.fillMode = kCAFillModeForwards;
swapanim.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionLinear];
[swapanimarray addObject:swapanim];
//text animation
CABasicAnimation *textanim = [CABasicAnimation animationWithKeyPath:@"contents"];
textanim.duration = duration;
textanim.fromValue = @"Hey";
textanim.toValue = @"Hello";
textanim.beginTime = start;
[textanimarray addObject:textanim];
// final time settings
prev_x = actual_x;
prev_y = actual_y;
start = start + duration;
totalDuration = start + duration;
}
}
CAAnimationGroup* group = [CAAnimationGroup animation];
[group setDuration:totalDuration];
group.removedOnCompletion = NO;
group.fillMode = kCAFillModeForwards;
[group setAnimations:animarray];
CAAnimationGroup* swapgroup = [CAAnimationGroup animation];
[swapgroup setDuration:totalDuration];
swapgroup.removedOnCompletion = NO;
swapgroup.fillMode = kCAFillModeForwards;
[swapgroup setAnimations:swapanimarray];
CAAnimationGroup* textgroup = [CAAnimationGroup animation];
[textgroup setDuration:totalDuration];
textgroup.removedOnCompletion = NO;
textgroup.fillMode = kCAFillModeForwards;
[textgroup setAnimations:textanimarray];
[ball addAnimation:group forKey:@"position"];
[swap addAnimation:flaggroup forKey:@"position"];
[text addAnimation:textgroup forKey:@"contents"];
[self.layer addSublayer:ball];
[self.layer addSublayer:swap];
[self.layer addSublayer:text];
}
さて...問題:
1) スワップ イメージはスワップごとに元に戻ります。したがって、A->B を交換すると、予想される継続時間内に A から B に移動することがわかりますが、その後 A に戻ります。これについて SO で多くのスレッドを読みましたが、機能させることができませんでした.
2) テキストレイヤーの文字列をタイミングを合わせて変更する...これはこのインフラストラクチャで可能ですか? 基本的に、例で説明されているように、最初の画像が移動するとすぐにテキストとスワップ画像を変更しようとしています。
3) CABasicAnimation のデリゲートを設定しても効果はありませんが、CAAnimationGroup には効果があります。その結果、アニメーションごとに、グループ全体だけで animationDidStop のようなイベントを管理することはできません。そうする別の方法はありますか?
4) 3) に続いて、CAAnimationGroup を使用して、イベントをインターセプトして停止/開始動作を作成することは可能ですか? 再生/停止ボタンが必要で、アニメーションを中断したところから再開したいとしましょう。
決定的な質問として、誰かが同様のことをしたかどうか、そして最も重要なのは、この方法 (CAAnimationGroup を使用) が実際に進むべき道なのか、それとも CAKeyFrameAnimation などを使用する方が良いのかを知りたいだけです。