2017-10-29 22 views
0

Ich bin ein bisschen verwirrt über das "Laden" oder Binden verschiedener Texturen für einzelne Objekte in meiner Szene.Binden Sie verschiedene Texturen für jedes Objekt

Dies ist die Art, wie ich die Textur gesetzt (die Textur von Festplatte geladen und Bindung):

setTexture (const std::string& t_filename) 
{ 
int width, height, nrChannels; 

glBindTexture(GL_TEXTURE_2D, m_TEX); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 

unsigned char* image = stbi_load(t_filename.c_str(), &width, &height, &nrChannels, 0); 

if (image) 
{ 
    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, width, height, 0, GL_RGB, GL_UNSIGNED_BYTE, image); 
    glGenerateMipmap(GL_TEXTURE_2D); 
} 
else 
{ 
    throw std::string("Texture could not get loaded. Abort"); 
} 
stbi_image_free(image); 

glBindTexture(GL_TEXTURE_2D, 0); 
} 

Die Funktion gehört zu einer Klasse Rectangle genannt.

Ich habe Membervariablen für das VAO, VBO und das Texturobjekt:

GLuint m_VAO{ 0 }; 
GLuint m_VBO{ 0 }; 
GLuint m_VEBO{ 0 }; 
GLuint m_TEX{ 0 }; 

So jede Instanz Rectangle hat eine Textur Objekt m_Tex.

Jedesmal, wenn ich meine Aufgabe in der Hauptfunktion zeichnen den Rahmen für das Zeichnen ich auf diese Weise:

glBindVertexArray(m_VAO); 
glBindTexture(GL_TEXTURE_2D, m_TEX); 
glDrawElements(GL_TRIANGLES, 6, GL_UNSIGNED_INT, nullptr); 
glBindVertexArray(0); 

Das Problem: Alle meine Objekte (sagen wir, ich habe 3 Rectangle Instanzen) verwenden die gleiche Textur, obwohl alle von ihnen ein eigenes Texturobjekt vor dem Zeichnen binden. Warum das?

Bearbeiten: Okay meine Schuld! Ich habe vergessen, die Textur-Objekt in meine setTexture Funktion wie das zu erzeugen:

glGenTextures(1, &m_TEX); 

nun wie erwartet Ich kann meine Texturen und „Switch“ zwischen ihnen geladen werden!

+0

Was eine Frage ist, dass dein Gedächtnis nicht unendlich ist, so wird es natürlich eine Grenze geben. –

+0

Antwort: Es ist nicht möglich. Die Anzahl der Texteinheiten hängt von der Hardware ab. 'GLint nein; glGetIntegerv (GL_MAX_TEXTURE_IMAGE_UNITS, & no) '. – Rabbid76

+0

Das einzige, was ich mir vorstellen kann, ist ['ARB_bindless_texture'] (https://www.khronos.org/registry/OpenGL/extensions/ARB/ARB_bindless_texture.txt) - siehe [Bindless Texture] (https: //www.khronos .org/opengl/wiki/Bindless_Textur). Aber ich denke, das ist noch nicht Teil des Standards und wird nicht von jeder Hardware unterstützt. – Rabbid76

Antwort

3

Wie ist es möglich, jede Textur für theoretisch unendliche Objekte am Anfang zu laden und dann einfach zwischen ihnen zu "wechseln"?

von nur einigen Textur Erstellen von Objekten, und sie binden, wenn Sie sie verwenden möchten. Textur Einheiten haben nichts damit zu tun.

// at init time 
GLuint texA, texB; 

// create texture A 
glGenTextures(1, &texA); 
glBindTexture(GL_TEXTURE_2D, texA); 
glTexParameter(...); glTexImage(...); 

// create texture B 
glGenTextures(1, &texB); 
glBindTexture(GL_TEXTURE_2D, texB); 
glTexParameter(...); glTexImage(...); 


// at draw time 
glBindTexture(GL_TEXTURE_2D, texA); 
glDraw*(...); // draw with texture A 
glDraw*(...); // still draw with texture A 

glBindTexture(GL_TEXTURE_2D, texB); 
glDraw*(...); // now draw with texture B 

Es ist nicht klar, welche m_TEX in Ihrem Code, aber es sieht aus wie eine Membervariable einer Klasse. Sie zeigen jedoch nicht an, zu welchen Klassen Ihre Codefragmente gehören. Daher ist es schwer zu erraten, was genau Sie tun. Für mich sieht es so aus, als hätten Sie nur eine einzige m_TEX Variable, was bedeutet, dass Sie sich nur einen Texturobjektnamen merken können und somit dieselbe Textur immer wieder verwenden können. Das heißt, Ihr Ladeprogramm generiert kein neues Texturobjekt, sondern verwendet einfach m_TEX.

Texture Einheiten sind für Multitexturing, um mehr als eine Textur zugleich zu binden (während eines einzigen Zeichenaufruf Bedeutung):

glActiveTexture(GL_TEXTURE0); 
glBindTexture(GL_TEXTURE_2D, texA); 
glActiveTexture(GL_TEXTURE1); 
glBindTexture(GL_TEXTURE_2D, texB); 
glDraw*(...) // draw with both texA and texB 

Dies wird natürlich erfordern Ein Shader, der beide Texturen verwendet und sie kombiniert (oder für verschiedene Arten von Daten verwendet), liegt ganz bei Ihnen.

+0

Ich habe meinen Beitrag bearbeitet –

Verwandte Themen