2012-08-08 18 views
11

Ich möchte rohe Texturdaten auf die Festplatte ausgeben (um später zurück zu lesen), und ich bin mir nicht sicher, ob glReadPixel von der aktuell gebundenen Textur lesen wird.Texturbytes mit glReadPixels lesen?

Wie kann ich den Puffer von meiner Textur lesen?

+0

Hey @Geri, meine Antwort Ihnen geholfen? – gergonzalez

Antwort

30

glReadPixels Funktion liest von Framebuffern, keine Texturen. Um eine Textur-Objekt zu lesen, müssen Sie verwenden glGetTexImage aber es ist in OpenGL ES nicht verfügbar :(

Wenn Sie den Puffer von Ihrer Textur lesen wollen, dann Sie es zu einem FBO (Framebuffer-Objekt binden kann) und die Verwendung glReadPixels:

//Generate a new FBO. It will contain your texture. 
glGenFramebuffersOES(1, &offscreen_framebuffer); 
glBindFramebufferOES(GL_FRAMEBUFFER_OES, offscreen_framebuffer); 

//Create the texture 
glGenTextures(1, &my_texture); 
glBindTexture(GL_TEXTURE_2D, my_texture); 
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL); 
glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_LINEAR); 
glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_LINEAR); 

//Bind the texture to your FBO 
glFramebufferTexture2DOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_TEXTURE_2D, my_texture, 0); 

//Test if everything failed  
GLenum status = glCheckFramebufferStatusOES(GL_FRAMEBUFFER_OES); 
if(status != GL_FRAMEBUFFER_COMPLETE_OES) { 
    printf("failed to make complete framebuffer object %x", status); 
} 

Sie dann nur, müssen glReadPixels rufen, wenn Sie von Ihrem Textur lesen möchten:

//Bind the FBO 
glBindFramebufferOES(GL_FRAMEBUFFER_OES, offscreen_framebuffer); 
// set the viewport as the FBO won't be the same dimension as the screen 
glViewport(0, 0, width, height); 

GLubyte* pixels = (GLubyte*) malloc(width * height * sizeof(GLubyte) * 4); 
glReadPixels(0, 0, width, height, GL_RGBA, GL_UNSIGNED_BYTE, pixels); 

//Bind your main FBO again 
glBindFramebufferOES(GL_FRAMEBUFFER_OES, screen_framebuffer); 
// set the viewport as the FBO won't be the same dimension as the screen 
glViewport(0, 0, screen_width, screen_height); 
+1

Ich kann bestätigen, dass dies auf einem Mac funktioniert, sobald alle OES-Suffixe entfernt sind – nuclearnova

2

Danke für die Antwort Gergonzale. Ich habe heute Morgen einige Zeit, um herauszufinden, wie dies mit 16-Bit-Texturen zur Arbeit zu kommen, kann dieser Code-Schnipsel an andere Personen nützlich sein GL_UNSIGNED_SHORT_5_6_5 Umwandlung GL_UNSIGNED_BYTE

glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, tSizeW, tSizeH, 0, GL_RGB, GL_UNSIGNED_SHORT_5_6_5, NULL); 
GLubyte* pixels = (GLubyte*) malloc(tSizeW * tSizeH * sizeof(GLubyte) * 2); 
glReadPixels(0, 0, tSizeW, tSizeH, GL_RGB, GL_UNSIGNED_SHORT_5_6_5, pixels); 

int index = (x*tSizeH + y)*2; 
unsigned int rgb = pixels[index + 1]*256 + pixels[index + 0]; 
unsigned int r = rgb; 
r &= 0xF800; // 1111 1000 0000 0000 
r >>= 11;  // 0001 1111 
r *= (255/31.); // Convert from 31 max to 255 max 

unsigned int g = rgb; 
g &= 0x7E0;  // 0000 0111 1110 0000 
g >>= 5;  // 0011 1111 
g *= (255/63.); // Convert from 63 max to 255 max 

unsigned int b = rgb; 
b &= 0x1F;  // 0000 0000 0001 1111 
//g >>= 0;  // 0001 1111 
b *= (255/31.); // Convert from 31 max to 255 max 
Verwandte Themen