2017-09-18 2 views
-1

J'essaye actuellement de rendre une texture à un plein écran QWindow (Qt 5.9.1).
Comme les textures étaient toutes noires, je voulais m'assurer que les indeces avaient raison de dire au fragment shader de rendre tous les pixels en rouge, mais apparemment une erreur est survenue ici.
Au lieu d'un quad, je reçois un triangle rouge dans le coin supérieur gauche de l'écran.
Je ne peux pas voir l'erreur que j'ai faite avec mon code, alors je vous demande de regarder par-dessus mon code.
Aussi ce qui pourrait être une raison pour obtenir seulement des textures noires, même si les textures que je télécharge avec glTexImage2D ont l'air bien et il n'y a pas d'erreurs dans glGetError.
Merci d'avance.
OpenGL rend le triangle au lieu du quad

contexte OpenGL Initialisation et QWindow:

int i; 
for(i=0;i<QApplication::screens().size();i++) 
{ 
    if(QApplication::screens().at(i)->name().compare(szScreenName)==0) 
     break; 
} 
if(i==QApplication::screens().size()) 
    i--; 

setGeometry(QApplication::screens().at(i)->availableGeometry()); 
showFullScreen(); 

setSurfaceType(QWindow::OpenGLSurface); 
QSurfaceFormat fmt; 
fmt.setSwapBehavior(QSurfaceFormat::SingleBuffer); 
fmt.setRenderableType(QSurfaceFormat::OpenGLES); 
setFormat(fmt); 
_pContext = new QOpenGLContext(this); 
_pContext->setFormat(fmt); 
//_pContext->setShareContext(QOpenGLContext::globalShareContext()); 
_pContext->create(); 

QObject::connect(this, &DLP::postRenderSignal, this, &DLP::render); 

_pContext->makeCurrent(this); 
initializeOpenGLFunctions(); 

//_pTexManager = new TextureManager(QOpenGLContext::globalShareContext()->functions()); 
_pTexManager = new TextureManager(this); 

char* szVertexShader =       "#version 110\n" 
               "attribute vec4 a_Position;\n" 
               "attribute vec2 a_TexCoord;\n" 
               "varying vec2 v_TexCoord;\n" 
               "void main()\n" 
               "{\n" 
               " gl_Position = a_Position;\n" 
               " v_TexCoord = a_TexCoord;\n" 
               "}\n"; 
char* szFragmentShader =      "#version 110\n" 
               "precision mediump float;\n" 
               "varying vec2 v_TexCoord;\n" 
               "uniform sampler2D u_Texture;\n" 
               "void main()\n" 
               "{\n" 
               " gl_FragColor = vec4(1.0,0.0,0.0,1.0);//texture2D(u_Texture, v_TexCoord);\n" 
               "}\n"; 

//_nProgram = linkShader(QOpenGLContext::globalShareContext()->functions(), szVertexShader, szFragmentShader); 
_nProgram = linkShader(this, szVertexShader, szFragmentShader); 

if(_nProgram!=0) 
{ 
    _nShaderSamplerLoc = glGetUniformLocation(_nProgram,"u_Texture"); 
    _nShaderTextureLoc = glGetAttribLocation(_nProgram,"a_TexCoord"); 
    _nShaderPositionLoc = glGetAttribLocation(_nProgram,"a_Position"); 
} 

glGenBuffers(2, _pBuffers); 

static const unsigned short pIndexData[] = { 0, 1, 2, 3 }; 
glBindBuffer(GL_ARRAY_BUFFER, _pBuffers[1]); 
glBufferData(GL_ARRAY_BUFFER, sizeof(pIndexData), pIndexData, GL_STATIC_DRAW); 

static const float pPosBuffer[20] = { 
     -1, 1, 0, 0, 0, 
     1, 1, 0, 1, 0, 
     -1, -1, 0, 0, 1, 
     1 -1, 0, 1, 1, 
}; 
glBindBuffer(GL_ARRAY_BUFFER, _pBuffers[0]); 
glBufferData(GL_ARRAY_BUFFER, 20*4, pPosBuffer, GL_STATIC_DRAW); 

Code rendu (DLP :: render):

if (!isExposed() || !_pContext) 
    return; 

_pContext->makeCurrent(this); 

glClearColor(0.0, 0.0, 0.0, 1.0); 
glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT|GL_STENCIL_BUFFER_BIT); 
glViewport(0,0,m_nWidth,m_nHeight); 

glEnable(GL_BLEND); 
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); 

glUseProgram(_nProgram); 

glBindBuffer(GL_ARRAY_BUFFER, _pBuffers[0]); 
// Load the vertex position 
glVertexAttribPointer(_nShaderPositionLoc, 3, GL_FLOAT, false, 5 * 4, (void*)0); 
glEnableVertexAttribArray(_nShaderPositionLoc); 
// Load the texture coordinate 
//glVertexAttribPointer(_nShaderTextureLoc, 2, GL_FLOAT, false, 5 * 4, (void*)(3 * 4)); 
//glEnableVertexAttribArray(_nShaderTextureLoc); 

glActiveTexture(GL_TEXTURE0); 
glBindTexture(GL_TEXTURE_2D, _pTexManager->getTexture(key)); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); 
glUniform1i(_nShaderSamplerLoc, 0); 
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, _pBuffers[1]); 
glDrawElements(GL_TRIANGLE_STRIP, 4, GL_UNSIGNED_SHORT, 0); 
glDisableVertexAttribArray(_nShaderPositionLoc); 
//glDisableVertexAttribArray(_nShaderTextureLoc); 

glFinish(); 

_pContext->swapBuffers(this); 



Edit:
De plus, ce problème ne se produit que lorsque j'ai plusieurs contextes OpenGL dans Qt, par exemple 4 objets Framebuffer, le QML Scenegraph et ce QWindow, il peut donc être un problème avec la façon dont Qt gère les contextes OpenGL.

+5

Photo rapide dans le noir ... votre 'glDawElements', ne devrait-il pas utiliser' GL_TRIANGLE_STRIP' au lieu de 'GL_TRIANGLES'? puisque GL_TRIANGLES attend 3 verts par triangle, et que vous ne lui donnez que 4 (3 pour le premier et 1 pour le dernier)? où une bande utiliserait 2 du sommet précédent? – Eddge

+0

Vous avez raison à ce sujet, je n'ai pas mis à jour ce segment de code. L'erreur est toujours là avec GL_TRIANGLE_STRIP. – Krustenkaese

+0

Je pense que votre ordre de sommet est faux pour une bande. Vous allez en haut à droite en bas à gauche. Vous avez besoin de bas, gauche -> haut, gauche -> bas, droite -> en haut à droite - un zig-zag. – Robinson

Répondre

0

Ok, la question est résolue:
Apparemment, j'ai eu quelques problèmes avec mes données de texture, qui avaient des données alpha étranges, donc avec la fonction de mélange activé, il n'a pas rendu les textures. La raison pour laquelle le rectangle n'a pas été rendu correctement était également une erreur de signe dans l'une des indeces.
Btw: Vogl est un outil très utile pour regarder la machine d'état OpenGL pour déboguer des applications.