< Tutorials
Version vom 14. Februar 2015, 23:40 Uhr von Mike (Diskussion | Beiträge) (Prinzip der einfachen Physik)


Ziel

Nach erfolgreichem Abschluss dieses Tutorials kannst du die Physik-Funktionen der Engine nutzen.


Vorwort

Bis zur Version 2.x gab es in der Engine Alpha nur eine sehr einfache Physik. Ein Objekt war entweder aktiv oder passiv. Aktive Objekte unterliegen der Schwerkraft und können passive Objekte nicht durchdringen. Aktive Objekte können von passiven Objekten "mitgenommen" werden.

Ab Version 3.0 wurde zusätzlich eine Newton'sche Physik eingeführt, d.h. Objekte können eine Masse und einen Impuls haben. Auf sie können Kräfte oder Kraftstöße einwirken und es kommt zu Impuls-Übertrag. Auch Reibung ist realisiert. Die neuen Physik-Funktionen in der Engine sind noch in der Entwicklung. Eine frühe Testversion ist bereits in der Engine enthalten, jedoch gibt es noch Lücken und Inkonsistenzen in den Physik-Funktionen.

Die hier demonstrierten Funktionen und Demo-Projekte funktionieren in der aktuellsten Pre-Version (Nightly). Sollte ein Bug gefunden werden, freuen wir uns über dein Feedback!

Die API (also die Nutzungsweise der Funktionen) wird sich nicht ändern.


Prinzip der einfachen Physik

Die Klasse Raum stellt für die einfache Physik zwei Möglichkeiten zur Verfügung:

  •   public void aktivMachen()
    
 Startet für dieses Objekt den einfachen Physik-Modus als aktives Objekt.
  •   public void passivMachen()
    
 Startet für dieses Objekt den einfachen Physik-Modus als passives Objekt.

Mit der Methode

public void neutralMachen()

kann der einfache Physik-Modus eines Objekts wieder abgeschaltet werden.

Die Grundlagen: Newton'sche Physik

Dieses Kapitel nutzt einige mechanische Konzepte, so wie

  • Geschwindigkeit / Masse
  • Impuls
  • Kräfte

und deren Zusammenhänge. Ein Grundwissen über deren Zusammenwirken ist sehr hilfreich für die Arbeit mit der Physik-Engine.

Ein gutes Modell für die meisten alltäglichen physikalischen, mechanischen Vorgänge ist die Newton'sche Mechanik. Diese wird auch in der Engine intern genutzt, um die physikalischen Vorgänge zu beschreiben, die während des Spiels geschehen.

Jedes Raum-Objekt hat eine Reihe von Physik-Methoden, mit denen man die Physik-Funktionen der Engine nutzen kann. Die Methode newtonschMachen() startet die Physik für ein Raum-Objekt:

Raum raum; //Ein beliebiges Raum-Objekt, das instanziiert ist.

//Starte die Physik für das Raum-Objekt. Hiermit geht es los.
raum.newtonschMachen();


Nachdem ein Raum-Objekt aktiviert wurde, kann man alle Physik-Methoden nutzen. Die Physik-Engine arbeitet intern mit den Standard-Einheiten der Physik. Hier ist eine Übersicht über die Methoden, die man an jedem (aktivierten) Raum-Objekt ausführen kann:

Methode Einheit (Parameter) Funktionsweise
public void setzeMeterProPixel (
                               float mpp)
Meter / Pixel Durch die Pixel-Pro-Meter-Konstante kann die Engine die Standard-Einheit Meter auf die interne Einheit Pixel übertragen. Die Eingabe gilt für die gesamte Physik. Beispiel-Eingaben:
  10: Ein Pixel = 10 Meter (riesiges Bild)
  0.02: 50 Pixel = 1 Meter
public void impulsHinzunehmen(
                               Vektor impuls)
kg * (m / s) Bewirkt einen Impuls-Übertrag auf das Objekt. Der Impuls sorgt (in der Regel) dafür, dass sich das Objekt bewegt. Beispiel-Eingabe:
  new Vektor(1,0.5f) : Wirkt einen Impuls von 1 kg*(m/s) nach Rechts und von 0,5 kg*(m/s) nach Unten aus.
public void geschwindigkeitHinzunehmen (
                               Vektor geschwindigkeit)
m / s Addiert zu der aktuellen Geschwindigkeit v_alt die Geschwindigkeit geschwindigkeit. Die neue Geschwindigkeit ist dann die Summe der beiden v_alt + geschwindigkeit.

Diese Funktion wirkt unabhängig von der Masse.

public void luftwiderstandskoeffizientSetzen (
                               float luftwiderstandskoeffizient)
N / ( (m/s) ^2 ) Setzt den sog. Luftwiderstandskoeffizienten für das Objekt in der Engine. Allgemein physikalisch ist der Luftwiderstands-Kraft eines Körpers F_w = 1/2 * [Dichte d. Luft] * c_w * [Querschnittsfläche] * v^2.

Die Engine vereinfacht dies, indem alle Konstanten zu dem einen Luftwiderstandskoeffizienten zusammengefasst werden: F_w = luftwiderstandskoeffizient * v^2. Für eine exakte physikalische Simulation wähle luftwiderstandskoeffizient = 1/2 * [Dichte d. Luft] * c_w * [Querschnittsfläche].

public void masseSetzen (
                               float masse)
kg Setzt die Masse für dieses Objekt. Diese wird z.B. bei Kollisionen und anderen Impuls-Überträgen mit einbezogen.
public void konstanteKraftSetzen (
                               Vektor kraft)
N = kg * (m/s^2) Setzt eine Kraft, die konstant auf das Objekt wirken soll. Beispiel:
  new Vektor(0, 9.81f) : lässt eine Schwerkraft von 9.81 N auf das Objekt wirken.
public void geschwindigkeitSetzen (
                               Vektor geschwindigkeit)
m / s Setzt direkt eine neue Geschwindigkeit für dieses Objekt. Die alte Geschwindigkeit wird hierbei einfach ignoriert und überschrieben.
public void einfluesseZuruecksetzen ()
* Setzt die konstant wirkende Kraft auf 0.
  • Setzt die Geschwindigkeit auf 0.
public void kraftAnwenden (
                               Vektor kraft,
                               float t_kraftuebertrag)
N = kg * m / s^2

s

Wendet die Kraft kraft innerhalb von t_kraftuebertrag Sekunden auf das Objekt an. Je schneller der Kraftübertrag (also je kürzer die Zeit), desto größer ist die Beschleunigung, die auf das Objekt wirkt.
public void beeinflussbarSetzen (
                               boolean beeinflussbar)
Ist dieser Wert false, kann dieses Objekt durch Kollision mit anderen Physik-Objekten nicht verschoben werden. So kann man Wände/Decken/Plattformen etc. implementieren. Dieser Wert ist standardmäßig true.

Mit diesen Methoden kann man die kompletten Physik-Features abrufen.


Jump n' Run

Dieser Bereich wird erst ab Version 4.0 produktiv nutzbar sein, da die zugehörigen Features der Engine noch nicht ausgereift sind.


Probleme?

Du findest ein kleines Beispiel-Projekt, das ein einfaches Billiard-Projekt implementiert.