Wann sollte ein Vertex-Array und wann ein VBO verwendet werden?

14

Ich versuche, mehr über Vertex-Arrays und Vertex-Buffer-Objekte zu erfahren , verstehe die Unterschiede jedoch nicht in Bezug auf:

  • Anwendungsfall (statische Geometrie wie Terrains, Geometrie, die jeden Frame wie ein Partikelsystem ändert usw.)
  • Performance
  • Portabilität (alte Grafikkarte, Konsolen, Geräte wie Android oder iPhone usw.)

einige Klarstellungen?

nkint
quelle
3
Für alle anderen, die hier ankommen, lesen
afuzzyllama

Antworten:

14

Hier ist ein anständiger Bericht über VBOs.

Performance

Hier ist eine gute Übersicht über die Aufrufsemantik.

Hier finden Sie einen weiteren guten Überblick über Leistungsprobleme. Darin sehen wir, dass VBOs performanter sind als Arrays.

Der Grund, warum wir VBOs bevorzugen, ist, dass die Daten auf die Karte geladen werden und Sie sie nicht bei jedem Frame übertragen müssen. Abhängig vom Typ des erstellten VBO können Sie dem Grafiktreiber Hinweise zur Verwendung geben (Write-Many, Read-Many vs. Write-Many, Never-Read usw.).

Verwendung

VBOs eignen sich hervorragend für statische Geometrie wie Gelände, von dem Sie nicht erwarten, dass es sich ändert, oder für instanziierte Geometrie.

Vertex-Arrays eignen sich für Daten, die sich häufig ändern, aber auch vom Host-Computer gelesen werden. Daher werden sie häufig zum direkten Rendern von Daten verwendet, die gerade bearbeitet werden (z. B. Laser-Entfernungsmesser-Datenpuffer). Wenn Sie nicht die Daten auf dem Host-Gerät lesen müssen (also nur auf die Karte schieben), sind VBOs im Nur-Schreib-Modus eine gute Option.

Portabilität

Clientseitige Vertex-Arrays Diese sind in OpenGL vor 3.0 verfügbar, in 3.0 nicht mehr unterstützt und in 3.1+ enthalten. OpenGL ES unterstützt sie (OpenGL ES 2 nicht).

VBOs Diese sind ab OpenGL 1.5 verfügbar. Dies ist die einzige Möglichkeit, Geometriedaten in OpenGL ES 2 (und damit in WebGL) zu speichern.

ChrisE
quelle
2
In diesem PerformanceTuning.pdf heißt es, dass VBOs "die Leistung in nicht optimalen Fällen beeinträchtigen können" ... aber es wird nicht näher darauf eingegangen. Irgendeine Idee, was diese Fälle sind? Ich habe einen Fall, in dem ich die Geometrie für jeden Frame aktualisieren muss, also frage ich mich, ob ein Vertex-Array in diesem Fall besser oder schlechter wäre als ein VBO. Danke.
Sidewinderguy
1
Lesen Sie opengl.org/sdk/docs/man/xhtml/glDrawElements.xml und opengl.org/wiki/GlDrawElements - Vertex-Arrays NICHT veraltet oder entfernt, sie werden ab OpenGL 4.x weiterhin unterstützt.
1
@vaxquis Clientseitige Vertex-Arrays sind veraltet. Serverseitige Vertex-Arrays sind dies nicht. VAOs sind etwas anderes und sollen den Staat retten. Nichts war falsch in der Post, könnte aber genauer sein, wenn es Client-Seite angeben. Aber ich denke, das war implizit.
concept3d
1
"Clientseitige Vertex-Arrays sind veraltet. Serverseitige Vertex-Arrays sind es nicht." "Vertex-Arrays Diese sind in OpenGL vor Version 3.0 verfügbar, in Version 3.0 veraltet und in Version 3.1+ nicht mehr verfügbar." "Sie können separate Arrays von Eckpunkten (...) vorab angeben und sie verwenden, um eine Folge von Grundelementen mit einem einzigen Aufruf von glDrawElements zu erstellen. Kern in Version 4.4" - Ich sehe Widersprüche in diesen Aussagen.
2
Geben Sie außerdem, bevor Sie sagen, dass etwas "veraltet" ist, die Quelle dieser Erklärung an, vorzugsweise in einem amtlichen Dokument. Das Zeigen von StackExchange auf StackOverflow als Beweis ist NICHT die Art und Weise, wie Wissenschaft funktioniert, und die Verteidigung mit "Ich denke, das war implizit" ist kein Argument. Niemand fragte nach Client / Server-Arrays, die Frage betraf Vertex-Arrays im weitesten Sinne im Vergleich zu VBO. Übrigens, ich habe nichts über VAO gesagt, woher stammt diese Idee?
11

(Ich füge dies hier hinzu, weil die Antwort von ChrisE sehr vieldeutig ist, was leider auf die Mehrdeutigkeit der ursprünglichen Frage zurückzuführen ist. Ich gehe jedoch davon aus, dass die Frage des OP den Titel "Wann sollten VAOs verwendet werden ? " Tragen sollte und wann man VBOs benutzt ".)

V ertex B Uffer O bjects (die eigentlich nicht unähnlich sind , von anderen Arten von B Uffer O bjects, beispielsweise U niversal B Uffer O bjects) eine Einrichtung zum Hochladen von Vertexdaten an die Grafikhardware.

V ertex A rray O bjects werden zusätzlich zu verwendet VBO s zu verbessern , um clientseitige (CPU-Seite) Leistung, indem die Anzahl der Anrufe benötigten Reduzierung einzelnen Vertex - Puffer und Re-Set Vertex erneut zu binden Attribute jedes Mal , wenn Sie möchten , ändern, um auf eine bestimmte Weise zu rendern. Anstatt all das zu tun, was bei jedem Frame funktioniert, führen Sie dies einmal (bei der Initialisierung) durch und binden dann einfach den entsprechenden VAO für jeden (Satz von) Zeichenaufruf (en) neu, der die zugeordneten Scheitelpunktattribute verwendet.

Trotzdem entbindet Sie die Verwendung von VAOs nicht von der zusätzlichen Verantwortung, glBindBuffer+ glBufferDatafür Daten zu tun , die jeden Frame ändern , z. B. Positionen / Rotationen / Transformationsmatrizen von Spieleinheiten. Nur wenn Sie vollständig statische Daten haben, müssen Sie diese nur glBindVertexArray(&vao) -> glDraw*(...) -> glBindVertexArray(0)rendern.

Ingenieur
quelle
+1 VAO ist ein schrecklicher und verwirrender Name, der mich immer daran erinnert, was für ein Durcheinander openGL geworden ist.
concept3d
1
Ich erinnere mich auch, dass ich eine Diskussion zu dieser Frage geführt habe (das meiste davon wurde gelöscht). Wieder ist das Problem mit der schrecklichen Terminologie von OpenGL. Ich habe auch Chris Antwort bearbeitet, um genauer zu sein.
concept3d