2017-03-08 3 views
0

사용자가 UIView를 끌 때 사용자가 드래그를 해제 할 때 두 줄이 희미하게 사라지는 애니메이션을 만들려고합니다.
따라서 나는 UIPanGestureRecognizer 액션 핸들러에서 호출하는 undrawLines (팬 제스처 시작에서 호출 됨)과 redrawLines (팬 제스 처 끝에서 호출 됨)의 두 가지 기능을 가지고 있습니다.CAShapeLayer 이상한 애니메이션 동작

func undrawLines() { 

    line1.opacity = 0.0 
    line2.opacity = 0.0 

    line1.removeAllAnimations() 
    line2.removeAllAnimations() 

    let opacityLine = CABasicAnimation(keyPath: "opacity") 
    opacityLine.fromValue = 1.0 
    opacityLine.toValue = 0.0 
    opacityLine.duration = 0.15 

    line1.add(opacityLine, forKey: "disappearLine1") 
    line2.add(opacityLine, forKey: "disappearLine2") 

    DispatchQueue.main.asyncAfter(deadline: .now() + 0.3, execute: { 
     mill.line1.removeFromSuperlayer() 
     mill.line2.removeFromSuperlayer() 
    }) 
} 

func redrawLines() { 

    line1.opacity = 1.0 
    line2.opacity = 1.0 

    print("redraw") 
    line1.removeAllAnimations() 
    line2.removeAllAnimations() 

    self.layer.addSublayer(line1) 
    self.layer.addSublayer(line2) 

    let opacityLine = CABasicAnimation(keyPath: "opacity") 
    opacityLine.fromValue = 0.0 
    opacityLine.toValue = 1.0 
    opacityLine.duration = 0.15 

    line1.add(opacityMill, forKey: "appearLine1") 
    line2.add(opacityMill, forKey: "appearLine2") 
} 

문제는 어떻게해야, 첫 번째 부분은 표시 redrawLinesundrawLines 애니메이션이 계속 실행되는 동안 호출되는 경우, 선이 이상한 행동을 보여 불투명도가 여기에 0
입니다 데모 점이다

:

답변

1

enter image description here

내가 여기 문제가 완료 핸들러와 경쟁 조건이라고 생각 : 두 번째는 버그를 보여줍니다

사용자가 풀어서 0.3 초의 시간 초과 전에 redrawLines이 호출되면이 호출이 여전히 호출되어 줄을 제거합니다.

func undrawLines() { 

    self.linesHidden = true // update state 

    line1.opacity = 0.0 
    line2.opacity = 0.0 

    line1.removeAllAnimations() 
    line2.removeAllAnimations() 

    let opacityLine = CABasicAnimation(keyPath: "opacity") 
    opacityLine.fromValue = 1.0 
    opacityLine.toValue = 0.0 
    opacityLine.duration = 0.15 

    line1.add(opacityLine, forKey: "disappearLine1") 
    line2.add(opacityLine, forKey: "disappearLine2") 

    DispatchQueue.main.asyncAfter(deadline: .now() + 0.3, execute: { [weak self] in 
     if self?.linesHidden == true { // check this is still what we want to do 
      mill.line1.removeFromSuperlayer() 
      mill.line2.removeFromSuperlayer() 
     } 
    }) 
} 

func redrawLines() { 

    self.linesHidden = false // update state 

    line1.opacity = 1.0 
    line2.opacity = 1.0 

    print("redraw") 
    line1.removeAllAnimations() 
    line2.removeAllAnimations() 

    self.layer.addSublayer(line1) 
    self.layer.addSublayer(line2) 

    let opacityLine = CABasicAnimation(keyPath: "opacity") 
    opacityLine.fromValue = 0.0 
    opacityLine.toValue = 1.0 
    opacityLine.duration = 0.15 

    line1.add(opacityMill, forKey: "appearLine1") 
    line2.add(opacityMill, forKey: "appearLine2") 
} 

당신은 분명이의 클래스에 인스턴스 VAR linesHidden을 추가해야합니다 :

당신은 아마 현재의 의도를 나타내는 상태 플래그를 유지하고 비동기 콜백을 확인하려면 너무 일한다 :)

+0

완전 감사합니다! – Codey