Как добавить анимированный слой по определенному индексу - PullRequest
0 голосов
/ 22 августа 2010

Я добавляю два слоя CAText к виду и анимирую один из них. Я хочу анимировать один слой над другим, но он не будет правильно расположен в иерархии слоев, пока анимация не закончится. Кто-нибудь может увидеть, что я сделал не так? Анимация работает, она просто работает за topcharlayer2, пока анимация не закончится.

- (CABasicAnimation *)topCharFlap
{
CABasicAnimation *flipAnimation;


flipAnimation = [CABasicAnimation animationWithKeyPath:@"transform"]; 
flipAnimation.toValue      = [NSValue valueWithCATransform3D:CATransform3DMakeRotation(1.57f, 1, 0, 0)];
flipAnimation.fromValue    = [NSValue valueWithCATransform3D:CATransform3DMakeRotation(0.0, 1, 0, 0)]; 
flipAnimation.autoreverses = NO; 
flipAnimation.duration     = 0.5f;
flipAnimation.repeatCount  = 10;


return flipAnimation;
}

- (id)initWithFrame:(CGRect)frame {
if ((self = [super initWithFrame:frame])) {
    [self setBackgroundColor:[UIColor clearColor]]; //makes this view transparent other than what is drawn.

    [self initChar];
}

return self;
}

static CATransform3D CATransform3DMakePerspective(CGFloat z)
{
CATransform3D t = CATransform3DIdentity;
t.m34 = - 1. / z;
return t;
}



-(void) initChar 
{
UIFont *theFont = [UIFont fontWithName:@"AmericanTypewriter" size:FONT_SIZE];

self.layer.sublayerTransform = CATransform3DMakePerspective(-1000.0f);

topHalfCharLayer2 = [CATextLayer layer];

topHalfCharLayer2.bounds = CGRectMake(0.0f, 0.0f, CHARACTERS_WIDTH, 100.0f);
topHalfCharLayer2.string = @"R";    
topHalfCharLayer2.font = theFont.fontName;
topHalfCharLayer2.fontSize = FONT_SIZE;
topHalfCharLayer2.backgroundColor = [UIColor blackColor].CGColor;
topHalfCharLayer2.position = CGPointMake(CGRectGetMidX(self.bounds),CGRectGetMidY(self.bounds));

topHalfCharLayer2.wrapped = NO;


topHalfCharLayer1 = [CATextLayer layer];


topHalfCharLayer1.bounds = CGRectMake(0.0f, 0.0f, CHARACTERS_WIDTH, 100.0f);
topHalfCharLayer1.string = @"T";


topHalfCharLayer1.font = theFont.fontName;
topHalfCharLayer1.fontSize = FONT_SIZE;

topHalfCharLayer1.backgroundColor = [UIColor redColor].CGColor;
topHalfCharLayer1.position = CGPointMake(CGRectGetMidX(self.bounds),CGRectGetMidY(self.bounds));
topHalfCharLayer1.wrapped = NO;
//topHalfCharLayer1.zPosition = 100;

[topHalfCharLayer1 setAnchorPoint:CGPointMake(0.5f,1.0f)];

[[self layer] addSublayer:topHalfCharLayer1 ];
[[self layer] insertSublayer:topHalfCharLayer2 atIndex:0];

[topHalfCharLayer1 addAnimation:[self topCharFlap] forKey:@"anythingILikeApparently"];

}

Представление, содержащее этот код, загружается контроллером представления в loadView. Метод initChar вызывается в методе представления initWithFrame. Цель - iOS4. Я не использую setWantsLayer, поскольку я читал, что UIView в iOS автоматически поддерживает слой и не требует этого.

Ответы [ 3 ]

1 голос
/ 26 августа 2010

Из списка рассылки Apple Quartz-Dev:

Обычно в 2D-случае addSublayer рисует новый слой над предыдущая. Тем не менее, я считаю, что этот механизм реализации не зависит от zPosition и, вероятно, просто использует что-то вроде алгоритм художника. Но как только вы добавите zPositions и 3D, я не думаю, что вы можете положиться исключительно на порядок слоев. Но мне на самом деле неясно если Apple гарантирует что-либо в том случае, если вы не установили zПозиции на ваших слоях, но с установленной матрицей трехмерного преобразования.

Итак, кажется, что я должен явно установить zPosition при применении 3D-преобразований к слоям.

1 голос
/ 23 августа 2010

На ум приходит пара мыслей:

  • Попробуйте добавить слой 'R' в иерархию слоев до того, как запустите анимацию.

  • Вместо вставки слоя 'T' в индекс 1, используйте [[self layer] addSublayer: topHalfCharLayer1]; до , добавьте его и затем вставьте для слоя 'R' с[[self layer] insertSublayer:topHalfCharLayer2 atIndex:0];

  • Вы пытались играть со слоем zPosition ?Это определяет визуальный внешний вид слоев.Это на самом деле не меняет порядок слоев, но изменит способ их отображения - например, какие слои находятся перед / за какими.

  • Я бы также предложил вам удалить анимациюкод, пока вы не получите порядок представления слоя отсортированы.Как только вы это сделаете, анимация должна просто работать.

Если у вас возникнут дополнительные проблемы, дайте мне знать в комментариях.

С уважением.

0 голосов
/ 30 марта 2017
/* Insert 'layer' at position 'idx' in the receiver's sublayers array.
 * If 'layer' already has a superlayer, it will be removed before being
 * inserted. */

open func insertSublayer(_ layer: CALayer, at idx: UInt32)
...