Как получить координаты вида во время анимации?

Я создал CAShapeLayer и добавил кубический путь Безье (с функцией addCurveToPoint:controlPoint1:controlPoint2:) и добавил небольшой вид на начальную точку этой кривой. После этого я создал CAKeyFrameAnimation и переместил этот небольшой вид из начальной точки кривой в конечную точку с анимацией. Я хочу получить центральную точку этого вида во время анимации. Есть идеи?

CGPoint start, p, p1,p2;
start = CGPointMake(0, 150);
p = CGPointMake(300, 150);
p1 = CGPointMake(50, 225);
p2 = CGPointMake(250, 75);
[self.bezierPath moveToPoint:start];
[self.bezierPath addCurveToPoint:p
                   controlPoint1:p1
                   controlPoint2:p2];

NSLog(@"self bezierpath = %@",self.bezierPath);
CAShapeLayer *shapeLayer = [CAShapeLayer layer];
shapeLayer.path = self.bezierPath.CGPath;
shapeLayer.fillColor = [UIColor clearColor].CGColor;
shapeLayer.strokeColor = [UIColor redColor].CGColor;
shapeLayer.lineWidth = 3.f;
[self.yellowView.layer addSublayer:shapeLayer];

self.sliderThumb = [[UIView alloc]initWithFrame:(CGRect){0,0,20,20}];
self.sliderThumb.backgroundColor = [UIColor blackColor];
self.sliderThumb.center = CGPointMake(0, 150);
[self.yellowView addSubview:self.sliderThumb];
CAKeyframeAnimation *animation = [CAKeyframeAnimation animation];
animation.keyPath = @"position";
animation.duration = 4.f;
animation.path = self.bezierPath.CGPath;
[self.sliderThumb.layer addAnimation:animation forKey:nil];
CALayer *layer = self.sliderThumb.layer.presentationLayer;
NSLog(@"layer coordinates %f", layer.frame.origin.x);

`


person passingnil    schedule 29.08.2016    source источник


Ответы (1)


presentationLayer слоя представления – это CALayer, которое фиксирует, где слой находится в середине анимации.

Например, если вы хотите получать обновления кадр за кадром, настройте CADisplayLink и проверьте presentationLayer в обработчике отображаемой ссылки:

CAKeyframeAnimation *animation = [CAKeyframeAnimation animationWithKeyPath:@"position"];
animation.duration = 4.0f;
animation.path = self.bezierPath.CGPath;
animation.delegate = self;                                  // so we know when animation finished
[self startDisplayLink];                                    // start display link
[self.sliderThumb.layer addAnimation:animation forKey:nil];

С участием:

@property (nonatomic, weak) CADisplayLink *displayLink;

А также:

// Called when animation stops (assuming you set the `delegate` for the animation).

- (void)animationDidStop:(CAAnimation *)theAnimation finished:(BOOL)flag {
    [self stopDisplayLink:self.displayLink];
}

/// Start the display link.

- (void)startDisplayLink {
    CADisplayLink *displayLink = [CADisplayLink displayLinkWithTarget:self selector:@selector(handleDisplayLink:)];
    [displayLink addToRunLoop:[NSRunLoop mainRunLoop] forMode:NSRunLoopCommonModes];
    self.displayLink = displayLink;
}

/// Stop the display link.
///
/// @parameter displayLink The display link to be stopped.

- (void)stopDisplayLink:(CADisplayLink *)displayLink {
    [displayLink invalidate];
}

/// The display link handler.
///
/// Called once for each frame of the animation.
///
/// @parameter displayLink The display link being handled.

- (void)handleDisplayLink:(CADisplayLink *)displayLink {
    CALayer *layer = self.sliderThumb.layer.presentationLayer;
    NSLog(@"layer coordinates %f", layer.frame.origin.x);
}
person Rob    schedule 29.08.2016
comment
Спасибо за ответ. Знаете ли вы, есть ли другой способ получить координаты этой кривой? Я хочу создать что-то вроде слайдера, но с изогнутой дорожкой. - person passingnil; 30.08.2016
comment
Здорово! Спасибо. @Роб - person passingnil; 30.08.2016