2017-04-19 3 views
0

I Viewcontroller mit Sternen Bewertung haben, die wie folgt aussieht (außer, dass es 10 Sterne sind)Glatte Animation mit Timer und Schleife in iOS-App

enter image description here

Wenn Benutzer öffnet Viewcontroller für ein Objekt, das kein Rating Ich möchte die Aufmerksamkeit des Benutzers auf diese Sterne auf sehr einfache Art und Weise lenken: animierte Hervorhebung von Sternen (Sie könnten ein solches Verhalten bei einigen Anzeigen in der realen Welt beobachten, wenn jeder Buchstabe nacheinander hervorgehoben wird).

  1. Ein Stern markiert
  2. Zwei Sterne
  3. hervorgehoben
  4. Drei Sterne
  5. hervorgehoben
  6. ......
  7. alle von ihnen ausschalten

Das ist also die Art und Weise, wie Ich mache es

func delayWithSeconds(_ seconds: Double, completion: @escaping() ->()) { 
    DispatchQueue.main.asyncAfter(deadline: .now() + seconds) { 
     completion() 
    } 
} 

func ratingStarsAnimation() { 
    for i in 1...11 { 
     var timer : Double = 0.6 + Double(i)*0.12 
     delayWithSeconds(timer) { 
      ratingStars.rating = (i < 10) ? Double(i) : 0 
     } 
    } 
} 

Was ist hier los? Ich habe eine Funktion namens "delayWithSeconds", die die Aktion verzögert und ich verwende diese Funktion, um jede Hervorhebung von Sternen zu verzögern. Und 0.6 ist die Anfangsverzögerung, bevor die Animation beginnt. Nachdem alle Sterne markiert sind, ist der letzte Schritt, die Hervorhebung aller Sterne zu deaktivieren. Dieser Code funktioniert, aber ich kann nicht sagen, dass es glatt ist.

Meine Fragen sind:

  1. Wie kann ich 0,6 + Doppel (i) * 0,12 zu erhalten glatte Animation fühlen ändern?
  2. Ich denke, dass meine Lösung mit Verzögerungen nicht gut ist - wie kann ich glatte Sterne Hervorhebung Aufgabe besser lösen?
+0

zeigen Ihnen, dass Animation, die Sie bisher erreicht haben und die eine, die Sie wollen. –

+0

Wie kann ich es zeigen? – moonvader

+0

Video per DropBox teilen. –

Antwort

1

Schauen Sie sich die CADisplaylink-Klasse an. Es ist ein spezieller Timer, der mit der Aktualisierungsrate des Bildschirms verbunden ist, bei iOS sind es 60 fps. Es ist das Rückgrat vieler Animationsbibliotheken von Drittanbietern.

Anwendungsbeispiel:

var displayLink: CADisplayLink? 
let start: Double = 0 
let end: Double = 10 
let duration: CFTimeInterval = 5 // seconds 
var startTime: CFTimeInterval = 0 

let ratingStars = RatingView() 

func create() { 
    displayLink = CADisplayLink(target: self, selector: #selector(tick)) 
    displayLink?.add(to: .main, forMode: .defaultRunLoopMode) 
} 

func tick() { 
    guard let link = displayLink else { 
     cleanup() 
     return 
    } 

    if startTime == 0 { // first tick 
     startTime = link.timestamp 
     return 
    } 

    let maxTime = startTime + duration 
    let currentTime = link.timestamp 

    guard currentTime < maxTime else { 
     finish() 
     return 
    } 

    // Add math here to ease the animation 

    let progress = (currentTime - startTime)/duration 
    let progressInterval = (end - start) * Double(progress) 

    // get value =~ 0...10 
    let normalizedProgress = start + progressInterval 


    ratingStars.rating = normalizedProgress 
} 

func finish() { 
    ratingStars.rating = 0 
    cleanup() 
} 

func cleanup() { 
    displayLink?.remove(from: .main, forMode: .defaultRunLoopMode) 
    displayLink = nil 
    startTime = 0 
} 

Als Start wird dies Ihre Animation ermöglicht glatter zu sein. Sie müssen noch eine Trigonometrie hinzufügen, wenn Sie eine Beschleunigung hinzufügen möchten, aber das sollte nicht zu schwierig sein.