OpenGL忽略四边形,使它们成为三角形 [英] OpenGL ignores Quads and makes them Triangles

查看:67
本文介绍了OpenGL忽略四边形,使它们成为三角形的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

这是我第二次制作游戏引擎,但是现在有点卡住了,因为我无法弄清楚为什么会发生这种情况,无论我发送什么对象,OpenGL只会在其上绘制白色三角形在屏幕中心,像这样.

我什至将我的旧代码从Renderer和Camera Objects上的最后一个引擎中复制下来,仍然表现相同,因此我猜测它与Render Script有关.

渲染器:

  Renderer2D :: Renderer2D(const Shader& shader){this-> shader =着色器;this-> Init();}Renderer2D ::〜Renderer2D(){glDeleteVertexArrays(1,& this-> QuadVAO);}void Renderer2D :: Render(纹理和纹理,iVec2位置,iVec2大小,浮动旋转,iVec3颜色){this-> shader.Use();iMat4模型;使用名称空间glm;模型=翻译(模型,iVec3(position.x,position.y,0.0f));/*模型=翻译(模型,iVec3(size.x * 0.5f,size.y * 0.5f,0.0f));模型=旋转(模型,旋转,iVec3(0.0f,0.0f,1.0f));模型=翻译(模型,iVec3(size.x * -0.5f,size.y * -0.5f,0.0f));*/模型= glm :: scale(model,iVec3(size.x,size.y,1.0f));this-> shader.SetMatrix4("model2D",model);this-> shader.SetVector3f("color2D",color);glActiveTexture(GL_TEXTURE0);texture.Bind();glBindVertexArray(this-> QuadVAO);glDrawArrays(GL_TRIANGLES,0,6);glBindVertexArray(0);}Renderer2D :: Init(){U16 VBO;浮点顶点[] = {//Pos//Tex0.0f,1.0f,0.0f,1.0f,1.0f,0.0f,1.0f,0.0f,0.0f,0.0f,0.0f,0.0f,0.0f,1.0f,0.0f,1.0f,1.0f,1.0f,1.0f,1.0f,1.0f,0.0f,1.0f,0.0f};glGenVertexArrays(1,& this-> QuadVAO);glGenBuffers(1,& VBO);glBindBuffer(GL_ARRAY_BUFFER,VBO);glBufferData(GL_ARRAY_BUFFER,sizeof(顶点),顶点,GL_STATIC_DRAW);glBindVertexArray(this-> QuadVAO);glEnableVertexAttribArray(0);glVertexAttribPointer(0,4,GL_FLOAT,GL_FALSE,4 * sizeof(float),(void *)0);glBindBuffer(GL_ARRAY_BUFFER,0);glBindVertexArray(0);} 

顶点着色器:

  #version 330内核在vec4顶点中布局(位置= 0);//< vec2位置,vec2 texCoords>vec2 TexCoords;统一的mat4 view2D;统一的mat4 model2D;均匀的mat4 projection2D;无效main(){TexCoords = vertex.zw;gl_Position = projection2D * view2D * mode2Dl * vec4(vertex.xy,0.0,1.0);} 


顶点着色器:

  #version 330内核在vec4顶点中布局(位置= 0);//< vec2位置,vec2 texCoords>vec2 TexCoords;统一的mat4 view2D;统一的mat4 model2D;均匀的mat4 projection2D;无效main(){TexCoords = vertex.zw;gl_Position = projection2D * view2D * model2D * vec4(vertex.xy,0.0,1.0);} 

片段着色器:

  #version 330内核在vec2 TexCoords中;出vec4 color2D;//修正错误!统一采样器2D image2D;统一的vec3 color2D;无效main(){color2D = vec4(color2D,1.0)* texture(image2D,TexCoords);} 

Resources.cpp

  Shader Resources :: LoadShaderFromFile(const char * vertexSource,const char * fragmentSource){使用命名空间std;字符串vertexCode;字符串fragmentCode;尝试 {ifstream vertexShaderFile(vertexSource);ifstreamfragmentShaderFile(fragmentSource);stringstream vShaderStream,fShaderStream;vShaderStream<<vertexShaderFile.rdbuf();fShaderStream<<fragmentShaderFile.rdbuf();vertexShaderFile.close();fragmentShaderFile.close();vertexCode = vShaderStream.str();fragmentCode = fShaderStream.str();}赶上(e例外){cout<<错误:: SHADER:无法读取着色器文件"<<std :: endl;}const char * vShaderCode = vertexCode.c_str();const char * fShaderCode = fragmentCode.c_str();着色器着色器;shader.Compile(vShaderCode,fShaderCode);返回着色器;} 

解决方案

着色器甚至无法编译.声明矩阵制服时,将使用名称 model2D view2D projection2D :

 统一的mat4 view2D;统一的mat4 model2D;均匀的mat4 projection2D; 

但是,当您使用矩阵时,则使用名称 view model projection :

  gl_Position =投影*视图*模型* vec4(vertex.xy,0.0,1.0); 


我建议检查着色器对象是否成功编译以及程序对象链接是否成功.

如果可以成功通过 glGetShaderiv 和参数 GL_COMPILE_STATUS .

例如

  GLuint shaderObj = ....;glCompileShader(shaderObj);GLint status = GL_TRUE;glGetShaderiv(shaderObj,GL_COMPILE_STATUS,& status);如果(状态== GL_FALSE){GLint logLen;glGetShaderiv(shaderObj,GL_INFO_LOG_LENGTH,& logLen);std :: vector<字符> log(logLen);GLsizei撰写;glGetShaderInfoLog(shaderObj,logLen,& write,log.data());std :: cout<<编译错误:"<<std :: endl<<log.data()<<std :: endl;} 

如果程序链接成功,可以通过 glGetProgramiv 和参数 GL_LINK_STATUS .

例如

  GLuint progObj = ....;glLinkProgram(progObj);GLint status = GL_TRUE;glGetProgramiv(progObj,GL_LINK_STATUS,& status);如果(状态== GL_FALSE){GLint logLen;glGetProgramiv(progObj,GL_INFO_LOG_LENGTH,& logLen);std :: vector<字符> log(logLen);GLsizei撰写;glGetProgramInfoLog(progObj,logLen,& write,log.data());std :: cout<<链接错误:"<<std :: endl<<log.data()<<std :: endl;} 

This is the second time I'm making a game engine, but I'm a little stuck right now, since I cannot figure out why this is happening, no matter what object I send, OpenGL only draws a White Triangle on the center of the screen, like this.

I've even coppied my old code from my last engine on the Renderer and the Camera Objects, still acts the same, so I´m guessing it has something to do with the Render Script.

Renderer:

Renderer2D::Renderer2D(const Shader& shader) {
    this->shader = shader;
    this->Init();
}

Renderer2D::~Renderer2D() {
    glDeleteVertexArrays(1, &this->QuadVAO);
}

void Renderer2D::Render(Texture & texture, iVec2 position, iVec2 size, float rotation, iVec3 color) {
    this->shader.Use();
    iMat4 model;

    using namespace glm;
    model = translate(model, iVec3(position.x, position.y, 0.0f));
    /*
    model = translate(model, iVec3(size.x * 0.5f, size.y * 0.5f, 0.0f));
    model = rotate(model, rotation, iVec3(0.0f, 0.0f, 1.0f));
    model = translate(model, iVec3(size.x * -0.5f, size.y * -0.5f, 0.0f));
    */
    model = glm::scale(model, iVec3(size.x, size.y, 1.0f));

    this->shader.SetMatrix4("model2D", model);
    this->shader.SetVector3f("color2D", color);

    glActiveTexture(GL_TEXTURE0);
    texture.Bind();

    glBindVertexArray(this->QuadVAO);
    glDrawArrays(GL_TRIANGLES, 0, 6);
    glBindVertexArray(0);
}

void Renderer2D::Init() {
    U16 VBO;

    float vertices[] = {
        // Pos      // Tex
        0.0f, 1.0f, 0.0f, 1.0f,
        1.0f, 0.0f, 1.0f, 0.0f,
        0.0f, 0.0f, 0.0f, 0.0f,

        0.0f, 1.0f, 0.0f, 1.0f,
        1.0f, 1.0f, 1.0f, 1.0f,
        1.0f, 0.0f, 1.0f, 0.0f
    };

    glGenVertexArrays(1, &this->QuadVAO);
    glGenBuffers(1, &VBO);

    glBindBuffer(GL_ARRAY_BUFFER, VBO);
    glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);

    glBindVertexArray(this->QuadVAO);
    glEnableVertexAttribArray(0);
    glVertexAttribPointer(0, 4, GL_FLOAT, GL_FALSE, 4 * sizeof(float), (void*)0);

    glBindBuffer(GL_ARRAY_BUFFER, 0);
    glBindVertexArray(0);
}

Vertex Shader:

#version 330 core
layout (location = 0) in vec4 vertex; // <vec2 position, vec2 texCoords>

out vec2 TexCoords;

uniform mat4 view2D;
uniform mat4 model2D;
uniform mat4 projection2D;

void main()
{
    TexCoords = vertex.zw;
    gl_Position = projection2D * view2D * mode2Dl * vec4(vertex.xy, 0.0, 1.0);
}


Edit:

Vertex Shader:

#version 330 core
layout (location = 0) in vec4 vertex; // <vec2 position, vec2 texCoords>

out vec2 TexCoords;

uniform mat4 view2D;
uniform mat4 model2D;
uniform mat4 projection2D;

void main()
{
    TexCoords = vertex.zw;
    gl_Position = projection2D * view2D * model2D * vec4(vertex.xy, 0.0, 1.0);
}

Fragment Shader:

#version 330 core
in vec2 TexCoords;
out vec4 color2D; //Fixed the error!

uniform sampler2D image2D;
uniform vec3 color2D;

void main()
{    
    color2D = vec4(color2D, 1.0) * texture(image2D, TexCoords);
}  

Resources.cpp

Shader Resources::LoadShaderFromFile(const char * vertexSource, const char * fragmentSource) {
    using namespace std;
    string vertexCode;
    string fragmentCode;

    try {
        ifstream vertexShaderFile(vertexSource);
        ifstream fragmentShaderFile(fragmentSource);
        stringstream vShaderStream, fShaderStream;

        vShaderStream << vertexShaderFile.rdbuf();
        fShaderStream << fragmentShaderFile.rdbuf();

        vertexShaderFile.close();
        fragmentShaderFile.close();

        vertexCode = vShaderStream.str();
        fragmentCode = fShaderStream.str();
    }
    catch (exception e) {
        cout << "ERROR::SHADER: Failed to read shader files" << std::endl;
    }

    const char *vShaderCode = vertexCode.c_str();
    const char *fShaderCode = fragmentCode.c_str();

    Shader shader;
    shader.Compile(vShaderCode, fShaderCode);

    return shader;
}

解决方案

You'r shader doesn't even compile. When you declare the matrix uniforms, then you use the names model2D, view2D and projection2D:

uniform mat4 view2D;
uniform mat4 model2D;
uniform mat4 projection2D;

But when you use the matrices, then you use the names view, model and projection:

gl_Position = projection * view * model * vec4(vertex.xy, 0.0, 1.0);


I recommend to check if the shader objects compiled successfully and if the program object link successfully.

If the compiling of a shader succeeded can be checked by glGetShaderiv and the parameter GL_COMPILE_STATUS.

e.g.

GLuint shaderObj = .... ;
glCompileShader( shaderObj );

GLint status = GL_TRUE;
glGetShaderiv( shaderObj, GL_COMPILE_STATUS, &status );
if ( status == GL_FALSE )
{
    GLint logLen;
    glGetShaderiv( shaderObj, GL_INFO_LOG_LENGTH, &logLen );
    std::vector< char >log( logLen );
    GLsizei written;
    glGetShaderInfoLog( shaderObj, logLen, &written, log.data() );
    std::cout << "compile error:" << std::endl << log.data() << std::endl;
}

If the linking of a program was successful can be checked by glGetProgramiv and the parameter GL_LINK_STATUS.

e.g.

GLuint progObj = ....;
glLinkProgram( progObj );

GLint status = GL_TRUE;
glGetProgramiv( progObj, GL_LINK_STATUS, &status );
if ( status == GL_FALSE )
{
    GLint logLen;
    glGetProgramiv( progObj, GL_INFO_LOG_LENGTH, &logLen );
    std::vector< char >log( logLen );
    GLsizei written;
    glGetProgramInfoLog( progObj, logLen, &written, log.data() );
    std::cout  << "link error:" << std::endl << log.data() << std::endl;
}

这篇关于OpenGL忽略四边形,使它们成为三角形的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆