【问题标题】:Texture loading problem OpenGL cant figure out why纹理加载问题 OpenGL 无法找出原因
【发布时间】:2021-04-29 15:02:37
【问题描述】:

我无法将纹理应用于图像。我就是找不到问题

没有纹理代码,代码也能正常工作。

主文件:

#include <GL/glew.h>
#include <GLFW/glfw3.h>
#include <iostream>
#include <filesystem>
#include <stb_image.h>

#include "Shaders/Shader.h"


bool isWireFrame = false;

const int SCREEN_WIDTH = 1280;
const int SCREEN_HEIGHT = 720;

void framebufferCallBack(GLFWwindow* window, int width, int height)
{
    glViewport(0, 0, width, height);
}

void keyCallBack(GLFWwindow* window, int key, int scancode, int action, int mods)
{
    if (key == GLFW_KEY_ESCAPE && action == GLFW_PRESS)
    {
        isWireFrame = !isWireFrame;
    }
}

int main(void)
{
    GLFWwindow* window;
    /* Initialize the library */

    if (!glfwInit())
    {
        std::cout << "GLFW did not init!" << std::endl;
        return EXIT_FAILURE;
    }
    /* Create a windowed mode window and its OpenGL context */
    window = glfwCreateWindow(SCREEN_WIDTH, SCREEN_HEIGHT, "Hello World", NULL, NULL);
    if (window == NULL)
    {
        glfwTerminate();
        return EXIT_FAILURE;
    }

    /* Make the window's context current */
    glfwMakeContextCurrent(window);

    GLenum err = glewInit();
    if (GLEW_OK != err)
    {
        /* Problem: glewInit failed, something is seriously wrong. */
        std::cerr << "Error: " << glewGetErrorString(err) << std::endl;
        return EXIT_FAILURE;
    }
    std::cerr << "Status: Using GLEW " << glewGetString(GLEW_VERSION) << std::endl;


    /*
     We have to tell OpenGL the size of the rendering window so OpenGL knows how we want to display the data and coordinates with respect to the window. We can set those dimensions via the glViewport function
    */
    glViewport(0, 0, SCREEN_WIDTH, SCREEN_HEIGHT);

    glfwSetFramebufferSizeCallback(window, framebufferCallBack);
    glfwSetKeyCallback(window, keyCallBack);

    Shader shader("Shaders/glsl/vert.glsl", "Shaders/glsl/frag.glsl");

    float vertices[] = {
       // positions         // tex coords
       0.5f,  0.5f, 0.0f,   1.0f, 1.0f,               // top right
       0.5f, -0.5f, 0.0f,   1.0f, 0.0f,               // bottom right
      -0.5f, -0.5f, 0.0f,   0.0f, 0.0f,               // bottom left
      -0.5f,  0.5f, 0.0f,   0.0f, 1.0f                // top left 
    };

    unsigned int indices[] = {
        0, 1, 3,
        1, 2, 3

    };

    unsigned int VBO, VAO, EBO, texture;

    glGenVertexArrays(1, &VAO);
    glBindVertexArray(VAO);

    glGenBuffers(1, &VBO);
    glBindBuffer(GL_ARRAY_BUFFER, VBO);
    glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);

    glGenBuffers(1, &EBO);
    glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, EBO);
    glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indices), indices, GL_STATIC_DRAW);

    glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 5 * sizeof(float), (void*)0);
    glEnableVertexAttribArray(0);
    glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 5 * sizeof(float), (void*)(3 * sizeof(float)));
    glEnableVertexAttribArray(1);

    glEnable(GL_TEXTURE_2D);

    glGenTextures(1, &texture);
    glActiveTexture(GL_TEXTURE0);
    glBindTexture(GL_TEXTURE_2D, texture);


    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_MIRRORED_REPEAT);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_MIRRORED_REPEAT);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);


    int width, height, nrChannels;
    unsigned char* data = stbi_load("Images/Crate.png", &width, &height, &nrChannels, 0);
    if (data)
    {
        glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, width, height, 0, GL_RGB, GL_UNSIGNED_BYTE, data);
        glGenerateMipmap(GL_TEXTURE_2D);
    }
    else 
    {
        std::cout << "Failed to load the texture" << std::endl;
    }
    stbi_image_free(data);

    glBindVertexArray(0);
    glBindBuffer(GL_ARRAY_BUFFER, 0);
    glBindBuffer(GL_TEXTURE_2D, 0);
    glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);


    /* Loop until the user closes the window */
    while (!glfwWindowShouldClose(window))
    {
        /* Render here */
        glClear(GL_COLOR_BUFFER_BIT);
        glClearColor(0.2f, 0.3f, 0.3f, 1.0f);

        float timeValue = glfwGetTime();
        float greenValue = (sin(timeValue) / 2.0f) + 0.5f;
        Vector4 colour(0.0f, greenValue, 0.0f, 1.0f);

        glBindTexture(GL_TEXTURE_2D, texture);


        shader.use();
        shader.setVec4("Colour", colour);
        glBindVertexArray(VAO);
        glDrawElements(GL_TRIANGLES, sizeof(indices) / sizeof(int), GL_UNSIGNED_INT, 0);

        glDrawArrays(GL_TRIANGLES, 0, 3);

        /* Swap front and back buffers */
        glfwSwapBuffers(window);

        /* Poll for and process events */
        glfwPollEvents();

        if (isWireFrame == true)
        {
            glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
        }
        else if (isWireFrame == false)
        {
            glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
        }

    }

    glDeleteVertexArrays(1, &VAO);
    glDeleteBuffers(1, &VBO);
    glDeleteBuffers(1, &EBO);
    glDeleteProgram(shader.ID);

    glfwTerminate();
    return 0;
}

片段着色器:

#version 330 core

out vec4 fragColour;

uniform vec4 Colour;

in vec2 TexCoord;

uniform sampler2D Texture;

void main()
{
    fragColour = texture(Texture, TexCoord);
} 

顶点着色器:

#version 330 core

layout (location = 0) in vec3 aPos;
layout (location = 1) in vec2 aTexCoord;

out vec2 TexCoord;

void main()
{
    gl_Position = vec4(aPos.xyz, 1.0);
    TexCoord = aTexCoord;
}

没有错误。

这是我绘制的对象。

[]

这是我要绘制的实际图像:

[]

图像应该是一个矩形,但它是一个三角形,我不知道为什么会这样,也许这些信息可以提供帮助。

编辑所以我发现我没有在

中使用正确的颜色格式
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, data);

但在格式参数之前是GL_RGB 而不是GL_RGBA

但现在我有一个半绘制的纹理:

【问题讨论】:

    标签: c++ opengl glsl glfw


    【解决方案1】:

    stride 参数是错误的。您的属性由 5 个组件(x、y、z、u、v)组成。因此步幅是5 * sizeof(float) 而不是8 * sizeof(float)

    另外纹理坐标的大小是2(u,v),而不是3:

    glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 5 * sizeof(float), (void*)0);
    glEnableVertexAttribArray(0);
    glVertexAttribPointer(1, 2, GL_FLOAT, GL_FALSE, 5 * sizeof(float), (void*)(3 * sizeof(float)));
    glEnableVertexAttribArray(1);
    

    由于图片格式是PNG,所以纹理格式是GL_RGBA而不是GL_RGB

    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, width, height, 0, GL_RGB, GL_UNSIGNED_BYTE, data);

    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, data);
    

    【讨论】:

    • 我完全忘记了!谢谢@Rabbid76
    猜你喜欢
    • 2010-12-27
    • 1970-01-01
    • 1970-01-01
    • 2015-12-22
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-02-21
    相关资源
    最近更新 更多