Warum OpenGL ES-Funktionen aus einem anderen Thread nicht aufgerufen werden können

Ich experimentiere mit dem Schreiben einer kleinen Spielmaschine für Android mit OpenGL ES. Ich habe ein Game Thread erstellt, das die Spielobjekte aktualisiert und das GLThread mit der Szene zeichnet. Ich hatte gelesen, dass du die Texturen in onSurfaceCreated Methode von GLSurfaceView laden musst. Ich folge dem, aber für einige Debugging-Zweck habe ich versucht, Texturen aus meinem Game Thread statt der GLThread zu laden. Ich habe keine Fehler und die Textur zeigte sich nicht auf dem Bildschirm. Ich habe meinen ganzen Tag damit verbracht, das Problem herauszufinden und schließlich lese ich hier unten

"Sei nur sicher, dass du OpenGL nur im Haupt-Thread benutzt." Sehr wichtig. Sie können nicht in Ihre Game Engine (die in einem anderen Thread sein kann) eine Textur-Lade-Funktion, die nicht mit dem gl-Thread synchronisiert ist. Setzen Sie dort eine Fahne, um Ihren Gl-Thread zu signalisieren, um eine neue Textur zu laden (zB können Sie eine Funktion in OnDrawFrame (GL gl) platzieren, die prüft, ob eine neue Textur geladen werden muss.

  • Android - Kamera Vorschau
  • Bypassing Google TTS Engine Initialisierung Verzögerung in Android
  • Erweiterbare Listenansicht Android, benutzerdefinierte Drawables
  • Mehrere TextViews aktualisieren sehr langsam
  • Android: Update ListView Items alle 1 Minute
  • Wie man einen Service neu starten, nachdem er von Apps wie "Advanced Task Killer" getötet wurde?
  • Ich werde meinen Code so ändern, dass die Texturen aus dem GL Thread geladen werden. Ich konnte einfach nicht verstehen warum ist es so? Warum funktionieren die OpenGL-Funktionen nicht aus einem anderen Thread?

    Ich weiß, wie man Threads erstellt, aber ich weiß nicht, was Synchronisation bedeutet. Der obige Auszug erwähnt: "Du kannst deine Game Engine nicht aufrufen (was in einem anderen Thread sein kann) eine Textur-Lade-Funktion, die nicht mit dem Gl-Thread synchronisiert ist." Also ich vermute, dass mein Game Thread nicht mit dem GL Thread synchronisiert werden kann. Ist es möglich, einen weiteren Thread zu erstellen, der mit dem GL Thread synchronisiert ist, damit GL-Funktionen von ihm aufgerufen werden können? Was soll ich lernen, diese Konzepte zu verstehen?

  • Android Link zu Markt aus einer anderen App
  • Dividing zwei Integers in Java gibt mir 0 oder 100?
  • Android NDK inkrementell bauen
  • Aspectj mit der androidbibliothek
  • Android CheckBox Text nicht angezeigt
  • Android Browser streckt Bild
  • One Solution collect form web for “Warum OpenGL ES-Funktionen aus einem anderen Thread nicht aufgerufen werden können”

    Quixoto's Kommentar ist am nächsten, denke ich. Der traditionelle Grund, dass OpenGL-Kontexte sind Thread spezifisch auf so ziemlich jede Plattform ist, dass OpenGL ist stark abhängig von Staaten und hat keine Semantik für eine Reihe von Änderungen atomar. So kann zum Beispiel der Draw-Vorgang auf einem Thread sein:

    glVertexPointer(... supply vertex positions ...) glTexCoordPointer(... provide texture positions ...) /* and supply a few other pointers, maybe bind a texture */ glDrawArrays(... draw some geometry ...) 

    Der endgültige Aufruf liefert also vorhersehbare Ergebnisse nur im Kontext der vorangegangenen Anrufe. Wenn du es glVertexPointer , dass das Bit des Codes pausiert wird, sagen wir, glVertexPointer , ein weiterer Faden hüpfen und viel die gleiche Sequenz, um seine Geometrie zu zeichnen, und dann wird dieser Code fortfahren, wird er mit ganz der falschen Geometrie ziehen, möglicherweise sogar veranlassen -of-bounds Speicherzugriffe, wenn einige der ersetzten Arrays kleiner als die Originale sind.

    Android liefert die EGL, die das gemeinsame Konzept einer OpenGL-Aktie-Gruppe unterstützt (obwohl implizit Sie einen vorhandenen Kontext liefern, den ein neuer Kontext in einer gemeinsamen Gruppe mit dem dritten Argument an eglCreateContext ). Wenn zwei Kontexte in einer Anteilsgruppe sind, dann hat jeder von ihnen einen unabhängigen Zustand und ist sicher, von nur einem Thread anzurufen, aber benannte Objekte wie Texturen oder Vertex-Pufferobjekte stehen jedem zur Verfügung. So können Sie mit Share-Gruppen OpenGL-Aktionen gleichzeitig auf mehreren Threads ausführen, um die Ergebnisse auf einem einzigen Thread kombinieren zu können.

    Das Binden eines Kontextes an einen einzelnen Thread ist also nicht so sehr ein Thema. Die Planung für das Problem in OpenGL selbst wäre auch ein Nicht-Starter, weil ein Teil des Grundes, dass OpenGL-Kontexte in einer OS-spezifischen Weise erstellt, verwaltet und entsorgt werden, dass einige Betriebssysteme dieses Zeug in radikal unterschiedlicher Weise mit anderen umgehen müssen Oder sind in der Lage, bessere Lösungen anzubieten, indem sie ihre eigenen einzigartigen Lösungen aussetzen.

    Das Android ist ein Google Android Fan-Website, Alles ├╝ber Android Phones, Android Wear, Android Dev und Android Spiele Apps und so weiter.