Wie Sie Lerp richtig nutzen können.
Lerp steht für lineare Interpolation und ist in Unity für die Suche nach einem gewünschten Wert zwischen zwei Werten bekannt.
Zum Zeitpunkt der Veröffentlichung dieses Beitrags wurde Lerp im deutschsprachigen Raum nur sehr dürftig erläutert, weshalb wir den Entschluss gefasst haben, diesen Beitrag zu schreiben.
Die Lerp-Funktion von Unity finden Sie in der folgenden Dokumentation.
Bei der Suche nach „Lerp“ stellen wir fest, dass Lerp in vielen Klassen implementiert ist, darunter die Vektoren 2, 3 & 4, Farbe, Quaternion und mehr. Es gibt auch eine verwandte „Slerp“, die „sphärische lineare Interpolation“. Wir werden uns aber vorerst auf Mathf.Lerp konzentrieren.
Nur, um Folgendes klarzustellen, wir sprechen hier in diesem Beitrag nicht über den ikonischen Charakter, Lerpz, von Unity.
Wenn man sich die Dokumentation ansieht, ist die Beschreibung zum Zeitpunkt der Veröffentlichung dieses Artikels sehr dünn und das Code-Beispiel für Lerp ist völlig verwirrend.
Wir warten schon seit Jahren auf eine Aktualisierung der Seite, aber leider vergebens.
Bei uns kommt Lerp zum Einsatz, wenn ein neuer Wert zwischen einem Start- und einem Endwert gefunden werden soll.
Ein häufiger Fall für die Verwendung von Lerp wäre, etwas zwischen zwei Punkten im Laufe der Zeit linear zu bewegen oder zu animieren. In diesem Fall haben wir einen bekannten Startpunkt (von), einen bekannten Endpunkt (bis) und wir haben die Kontrolle über unseren Zeitwert (t).
Wenn wir etwas mit Lerp bewegen, senden wir Mathf.Lerp einfach unsere Startposition, unsere Endposition und die Zeit, die während des Verschiebevorgangs verstrichen ist, normalerweise geändert durch einen Geschwindigkeitswert, um zu steuern, wie schnell der Übergang vom Start zum Ziel erfolgt. Lerp gibt uns dann zurück, wo auf diesem Weg zwischen dem Start- und Endpunkt unser Objekt ist.
Sehen wir uns die Signatur an:
Wir sehen, dass Lerp einen Float-Wert zurückgibt. Wir geben Lerp ein „to“, ein „from“ und ein „t“.
Beachten Sie, dass „t“ zwischen 0 und 1 geklemmt ist.
… dies bedeutet, dass wir jeden gewünschten Wert zwischen „von“ und „bis“ auf Basis des Wertes von „t“ finden können, solange „t“ zwischen „0“ und „1“ liegt. „0“ ist der Startpunkt, „1“ ist der Endpunkt und jeder Wert zwischen „0“ und „1“ entspricht dem Wert zwischen Anfang und Ende.
Jetzt beginnt die Verwirrung,
Das Code-Beispiel sieht so aus:
Wo dieses Beispiel fehlschlägt, ist die Verwendung von raw Time.time.
Wenn neue Benutzer diesen Code greifen und versuchen, ihn zu verwenden, sehen sie keine Veränderung und das Objekt wird offenbar sofort auf den „to“-Wert umgeschlagen. Dies liegt hauptsächlich daran, dass die Zeit von „0“ bis „1“ in 1 Sekunde erfolgt und es dauert in der Regel mehr als 1 Sekunde, bis die Testszene einsatzbereit ist.
Auch das macht als richtiger Anwendungsfall keinen Sinn. Warum würde eine Lerp-Berechnung jemals in einem Spiel oder einer Anwendung ab dem ersten Frame verwendet und der Zeitpunkt der Berechnung nicht geändert werden?
Um eine korrekte Erklärung von Lerp zu bekommen, müssen wir eine eingestellte Startzeit sehen und dann die Imkrementierung der Zeit über die Zeit, vom Anfang bis zum Ende, vorzugsweise mit einem Geschwindigkeitswert, um sie zu ändern.
Verständlicherweise ist das ein kompliziertes Beispiel, aber der Code sollte folgendermaßen geändert werden:
Indem wir eine „Startzeit“ angeben, sehen wir den Beginn des Übergangs. Nur den Start zu verzögern, ist jedoch nicht ausreichend. Der wichtigste Teil ist es, das wir kontrollieren können, wann wir unser Lerp umsetzen. Dies zeigt uns, dass wir dies nun mit einem Tastendruck, einem Button oder einem Ereignis einleiten können und das kann jederzeit im Spiel geschehen.
Indem wir eine „Übergangsgeschwindigkeit“ hinzufügen, können wir sehen, dass wir die Kontrolle darüber haben, wie schnell der Übergang stattfindet. Wir können die Geschwindigkeit unseres Übergangs kontrollieren:
Lerp wird häufig auf eine bestimmte Weise missbraucht.
Dies liegt oft an dem ursprünglichen Beispielcode, von dem viele Leute annahmen, dass dieser defekt war. Um dieses vermutlich kaputte Beispiel zu beheben, wurde Time.deltaTime anstelle von Time.time verwendet.
Ein gängiges Beispiel war:
Dies hat einige interessante Auswirkungen. Es generiert eine Art „Lockerungs-“ oder „Dämpfungseffekt“ über den Übergang des Objekts.
Das erste, worüber man nachdenken sollte, ist Time.deltaTime. Sie nähert sich keiner Zahl. Es geht nicht von 0 auf 1, sondern ist ein ziemlich konstanter Wert, solange das Spiel mit einer konstanten Framerate läuft. Das bedeutet, dass in jedem Frame der Wert von Time.deltaTime in der Nähe des gleichen Wertes „schwebt“. Wenn wir die Position der Transformation nicht in jedem Frame eingeben würden, würde sich der Lerp nicht auf einen „to“-Wert zubewegen, sondern in der Nähe eines einzelnen Wertes wackeln.
Versuchen Sie das:
… und das Testobjekt wackelt einfach auf Basis der aktuellen Bildrate.
Das erste Beispiel für die Verwendung von Time.deltaTime funktioniert, da bei jedem Frame der Startpunkt auf die aktuelle neue Position der Transformation zurückgesetzt wird. Das bedeutet, dass für jeden Frame die Berechnung im Wesentlichen neu gestartet wird. Die Glättung oder Dämpfung ergibt sich aus der Tatsache, dass sich das Ziel nicht ändert, so dass das Testobjekt mit jedem Frame einen kleinen inkrementellen Wert in Richtung des Zielwertes verschiebt. Die Gefahr dabei ist: Das Testobjekt wird niemals den Zielwert erreichen.
Wenn dieses erste Beispielskript auf ein Testobjekt gelegt wurde und die Transformation zur Laufzeit beobachtet wurde, lange nachdem das GameObject scheinbar „gestoppt“ war, sind noch kleine inkrementelle Änderungen an der Position der Transformation sichtbar. Diese winzigen Werte werden weiterhin in Inkremente aufgeteilt, bis der Grenzwert für den Float-Wert erreicht ist, was die gesamte Zeit in Anspruch nimmt.
Kann ich Lerp dennoch für eine sanfte Dämpfung verwenden?
Ja, können wir, aber wir müssen uns dessen bewusst sein, was wir tun.
Wir müssen uns bewusst sein, dass wir Lerp im Wesentlichen missbrauchen, um mit Time.deltaTime und dem Zurücksetzen unserer Startposition eine gleichmäßige Dämpfung zu erzielen.
Ist das nicht der Schlüssel zu so vielen Dingen im Leben? Wir können die Regeln brechen, sobald wir wissen, warum sie da sind?
Damit dieser „missbrauchte“ Code funktioniert, müssen wir eine „fast dort“ Schwelle erkennen und dann den Lerp stoppen.
… enthalten wir auch den Bewegungscode mit einem einfachen Check:
Anbei der komplette Code:
Wir hoffen, dass das hilft, Lerp ein wenig besser zu erklären, als es in den Docs der Fall ist.
Vielen Dank für ihren Besuch.