2013-05-15 1 views
2

내 앱은 정지 사진을 찍고 말하기 영역을 움직여 이야기를 에뮬레이션합니다. 그러나 1/4 정도의 시간 동안, 일부 숨겨진 달력은 애니메이션 전체에서 계속 깜박입니다.CALayers를 사용하는 CAAnimation이 가끔씩 깜박임 애니메이션 (비디오 포함)을 만듭니다.

다음은 앱이 works properly 일 때 보이는 모습입니다. 다음은 앱이 glitches 일 때의 모습입니다. 편집 : a better video

문제가 경로와 관련 있다고 가정합니다. 앱에서 사용자는 입 영역 (동영상에 간략히 표시) 주위에 경로를 만들고 이것이 애니메이션 영역이됩니다. 때로는 경로가 매끄러운 애니메이션이되고 다른 때에는 위의 결함이 발생합니다. 또한 "뒤로"키를 누르고 애니메이션이있는 컨트롤러를 다시로드하려고하면 글리치가 지속되는 반면 다시로드하기 전에 경로를 변경하면 가끔씩 사라집니다. 때로는 이미지 A를하지만 이미지 B 작동되며, 다른 시간 그것은 것입니다 -

  • 이미지 유형/소스 :이 경로와 관련이없는 것 경우

    , 내가 제거 한 범인 중 일부입니다 이미지 b는 작동하지만 a는 작동하지 않습니다. 나는 사진 라이브러리 에서뿐만 아니라 인터넷에서 구한 이미지 이미지를 시도했습니다. 시뮬레이터 대

  • 아이폰 - 문제는 사진의

  • 수는 애니메이션 두 장치에서 발생 - 때때로 첫 시도에서 일어날 것입니다; 5 번이나 6 번 시도에서 다른 시간에 일어날 것입니다.

아래에 애니메이션으로 표시 할 코드가 나와 있습니다. 먼저 모든 검정색의 레이어를 만들고 그림과 입 영역을 뺀 레이어, 그리고 마지막으로 입 영역의 레이어를 만듭니다. 그런 다음 입 레이어의 위치를 ​​이동하여 변위가 검은 색이되고 입을 벌린 것처럼 보입니다.

EDIT : 또한 얼굴 레이어에서 마스크를 제거하여 입 구멍을 제거하면 애니메이션이 부드럽게 실행됩니다. 여기

- (id)initWithFrame:(CGRect)frame leftPt:(CGPoint)point0 rightPt:(CGPoint)point2 vertex1:(CGPoint)vertex1 vertex2:(CGPoint)vertex2 andPicture:(UIImage *)pic{ 

    self = [super initWithFrame:frame]; 
    if (self) { 

     p0 = point0; 
     p2 = point2; 
     v1 = vertex1; 
     v2 = vertex2; 
     picture = pic; 

     [self addBlackLayer]; 
     [self addFaceLayer]; 
     [self addMouthLayer]; 

     self.opaque = YES; 
    } 
    return self; 
} 
- (void)addBlackLayer { 

    CALayer *blackLayer = [CALayer layer]; 
    blackLayer.frame = self.bounds; 
    blackLayer.backgroundColor = [UIColor blackColor].CGColor; 
    [self.layer addSublayer:blackLayer]; 

} 
- (void)addFaceLayer { 

    CALayer *faceLayer = [CALayer layer]; 
    faceLayer.frame = self.bounds; 
    faceLayer.contents = (id)[picture CGImageWithProperOrientation]; 
    CAShapeLayer *faceMask = [CAShapeLayer layer]; 
    CGMutablePathRef fPath = CGPathCreateMutable(); 
    CGPathMoveToPoint(fPath, NULL, CGRectGetMinX(self.bounds), CGRectGetMinY(self.bounds)); 
    CGPathAddLineToPoint(fPath, NULL, CGRectGetMaxX(self.bounds), CGRectGetMinY(self.bounds)); 
    CGPathAddLineToPoint(fPath, NULL, CGRectGetMaxX(self.bounds), CGRectGetMaxY(self.bounds)); 
    CGPathAddLineToPoint(fPath, NULL, CGRectGetMinX(self.bounds), CGRectGetMaxY(self.bounds)); 
    CGPathAddLineToPoint(fPath, NULL, CGRectGetMinX(self.bounds), CGRectGetMinY(self.bounds)); 
    CGPathMoveToPoint(fPath, NULL, p0.x, p0.y); 
    midpt = CGPointMake((p2.x + p0.x)/2, (p2.y+ p0.y)/2); 
    CGPoint c1 = CGPointMake(2*v1.x - midpt.x, 2*v1.y - midpt.y); //control points 
    CGPoint c2 = CGPointMake(2*v2.x - midpt.x, 2*v2.y - midpt.y); 

    CGPathAddQuadCurveToPoint(fPath, NULL, c1.x, c1.y, p2.x, p2.y); 
    CGPathAddQuadCurveToPoint(fPath, NULL, c2.x, c2.y, p0.x, p0.y); 

    faceMask.path = fPath; 
    faceLayer.mask = faceMask; 
    [faceMask setFillRule:kCAFillRuleEvenOdd]; 
    [self.layer addSublayer:faceLayer]; 
    CGPathRelease(fPath); 

} 

- (void)addMouthLayer { 

    CGMutablePathRef mPath = CGPathCreateMutable(); 
    CGPathMoveToPoint(mPath, NULL, p0.x, p0.y); 
    midpt = CGPointMake((p2.x + p0.x)/2, (p2.y+ p0.y)/2); 
    CGPoint c1 = CGPointMake(2*v1.x - midpt.x, 2*v1.y - midpt.y); //control points 
    CGPoint c2 = CGPointMake(2*v2.x - midpt.x, 2*v2.y - midpt.y); 

    CGPathAddQuadCurveToPoint(mPath, NULL, c1.x, c1.y, p2.x, p2.y); 
    CGPathAddQuadCurveToPoint(mPath, NULL, c2.x, c2.y, p0.x, p0.y); 

    self.mouthLayer = [CALayer layer]; 
    CAShapeLayer *mouthMask = [CAShapeLayer layer]; 
    self.mouthLayer.frame = self.bounds; 
    self.mouthLayer.contents = (id)[picture CGImageWithProperOrientation]; 
    mouthMask.path = mPath; 
    mouthMask.frame = mouthLayer.bounds; 
    self.mouthLayer.mask = mouthMask; 
    [self.layer addSublayer:mouthLayer]; 
    self.mouthLayer.frame = CGRectMake(mouthLayer.frame.origin.x, mouthLayer.frame.origin.y, mouthLayer.frame.size.width, mouthLayer.frame.size.height); 
    CGPathRelease(mPath); 

은 (당신이 시도 알고하지 않습니다) 그냥 다른 방식 뷰 컨트롤러

- (CAAnimation *)createAnimationWithRepeatCount:(int)count { 

    CGPoint convertedStartingCenter = [self.view convertPoint:animatedFace.center toView:animatedFace]; 
    CGPoint endPt = CGPointMake(convertedStartingCenter.x, convertedStartingCenter.y + 15); 

    CABasicAnimation *mouthDown = [CABasicAnimation animationWithKeyPath:@"position"]; 
    mouthDown.duration = ANIMATION_TIME; 
    mouthDown.beginTime = 0; 
    mouthDown.fromValue = [NSValue valueWithCGPoint:convertedStartingCenter]; 
    mouthDown.toValue = [NSValue valueWithCGPoint:endPt]; 

    CABasicAnimation *mouthUp = [CABasicAnimation animationWithKeyPath:@"position"]; 
    mouthUp.duration = ANIMATION_TIME; 
    mouthUp.beginTime = ANIMATION_TIME; 
    mouthUp.fromValue = [NSValue valueWithCGPoint:endPt]; 
    mouthUp.toValue = [NSValue valueWithCGPoint:convertedStartingCenter]; 

    CAAnimationGroup *totalAnimation = [CAAnimationGroup animation]; 
    [totalAnimation setAnimations:[NSArray arrayWithObjects:mouthDown,mouthUp, nil]]; 
    [totalAnimation setDuration:2*ANIMATION_TIME]; 
    [totalAnimation setRemovedOnCompletion:NO]; 
    [totalAnimation setFillMode:kCAFillModeForwards]; 
    totalAnimation.repeatCount = count; 

    return totalAnimation; 

} 
+0

필자는 오타가 있는지, 문제가 해결되는지에 대해서는 잘 모르겠습니다. 하지만 반환 유형을 CAAnimation에서 CAAnimationGroup으로 변경해야합니다. – danypata

+0

아니요. – Mahir

+0

정확히 무슨 일이 일어나는지보기가 어렵습니다. 영화에서 그것은 경로가 이미지에서 구멍을 만들지 못한 것 같습니다. 그렇지 않다면 애니메이션을 느리게 할 수 있습니까? –

답변

0

에서 애니메이션을 생성하는 코드입니다 만 CABasicAnimation를 사용하여 클래스를 설정할 수 있습니다 애니메이션 위임자로, 위임 메서드에서 다음을 시작하려고 할 수 있습니다 CABasicAnimation. 시험을 보지 않았다면 나는 당신에게 모범을 보일 수 있습니다.

+0

하나의 cabasicanimation 만 사용했을 때 문제가 여전히 발생했습니다. – Mahir

+0

비슷한 상황입니까? http : // stackoverflow.co.kr/questions/1102896/switching-cabasicanimation-on-the-position-property-mid-animation-a-flick – Mahir

+0

예, 귀하의 행동과 같은 것 같습니다. 트랜잭션을'잠그고'잠금을 해제하려고 시도해야합니다. – danypata

관련 문제