2015-04-28 12 views
18

Ich habe Code arbeiten glMapBufferRange() von OpenGL-ES 3.0 auf Android verwenden, die wie folgt aussehen:Sichere Nutzung von glMapBufferRange() auf Android/Java

glBindBuffer(GL_ARRAY_BUFFER, myVertexBufferName); 
    glBufferData(GL_ARRAY_BUFFER, myVertexBufferSize, null, GL_STATIC_DRAW); 
    ByteBuffer mappedBuffer = (ByteBuffer)glMapBufferRange(
    GL_ARRAY_BUFFER, 
    0, myVertexBufferSize, 
    GL_MAP_WRITE_BIT | GL_MAP_INVALIDATE_BUFFER_BIT); 

    // [fill buffer...] 

    glUnmapBuffer(GL_ARRAY_BUFFER); 

Meine Frage ist über einziehe das Ergebnis glMapBufferRange() zu ByteBuffer auf die dritte Zeile. glMapBufferRange() ist declared to return a Buffer:

public static Buffer glMapBufferRange (int target, int offset, int length, int access)

Auf meiner Testplattform die Funktion eine Unterklasse von ByteBuffer so die Gussarbeiten zurückkehrt, sondern macht diese Annahme für alle Plattformen oder Android-Versionen OpenGL-ES unterstützt 3+ Doesn Es scheint mir sehr sicher zu sein. Obwohl es vernünftig erscheint, habe ich keine Dokumentation gefunden, die es garantiert, und wenn es garantiert war, scheint es so, als ob die Funktion als ByteBuffer zurückgegeben werden sollte.

Was ist der korrekte Weg (vorzugsweise unterstützt durch die Dokumentation) der Verwendung der Buffer, die von glMapBufferRange() zurückgegeben wird?

Antwort

6

Wie Sie bereits festgestellt haben, fehlt die Dokumentation. Aber es gibt noch eine ziemlich schlüssige Referenz: Die Implementierung der OpenGL-Java-Bindungen ist Teil des öffentlichen Android-Quellcodes.

Wenn Sie bei der Umsetzung des JNI-Wrapper suchen glMapBufferRange(), die in der Datei ist glMapBufferRange.cpp, können Sie sehen, dass der Puffer durch den Aufruf eine Funktion mit dem Namen NewDirectByteBuffer() zugeordnet ist. Basierend darauf ist es sicher anzunehmen, dass der Puffer tatsächlich ein ByteBuffer ist.

Während Anbieter den Android-Code ändern können, scheint es sehr unwahrscheinlich, dass jemand das Verhalten der Java-Bindungen ändern würde (außer vielleicht um Bugs zu beheben). Wenn Sie besorgt sind, dass die Umsetzung späteren Versionen Android verändern könnte, können Sie sicherlich eine Standard-Java-Typprüfung verwenden:

Buffer buf = glMapBufferRange(...); 
ByteBuffer byteBuf = null; 
if (buf instanceof ByteBuffer) { 
    byteBuf = (ByteBuffer)buf; 
} 

Oder könnten Sie aufwändigere Reflexion verwenden, beginnend mit getClass() auf dem zurückgegebenen Puffer aufruft. Die nächste Frage ist natürlich, was Sie tun, wenn der zurückgegebene Puffer kein ByteBuffer ist. Es ist wirklich der einzige Typ, der für mich einen Sinn ergibt.

+0

+1 für die Implementierung gehen. Die Implementierung könnte sich jedoch zumindest in der Theorie ändern. Gibt es eine Möglichkeit, 'glMapBufferRange()' praktisch zu verwenden, ohne Annahmen über die Implementierung zu machen? Oder ist diese Funktion nur falsch angegeben? – rhashimoto

+0

@rhashimoto Ich habe etwas Inhalt hinzugefügt. Aber dieser Teil war dir wahrscheinlich schon klar. –

+0

Ich denke, die meisten Leute haben nicht die Möglichkeit, ES 3.0+ zu verwenden oder OpenGL über JNI für etwas Ernsthaftes zu tun. Ich habe ein Kopfgeld für mehr Aufmerksamkeit eröffnet. – rhashimoto

Verwandte Themen