The texture is not displayed or is displayed wrong

37 Views Asked by At

Initially, I drew a triangle and used color. Now I have replaced the color with a texture, fixed the code, and here it starts: On the emulator I see the texture in full screen, although I limit it to 100px. I don't see anything on my physical device

Code:

const char* vertexShaderSource =
        "uniform mat4 projection;\n"
        "\n"
        "attribute vec3 position;\n"
        "attribute vec2 texCoord;\n"
        "varying vec2 fragmentTexCoord;\n"
        "void main()\n"
        "{\n"
        "    gl_Position = projection * vec4(position, 1.0);\n"
        "    fragmentTexCoord = texCoord;\n"
        "}\n";

const char* fragmentShaderSource =
        "varying vec2 fragmentTexCoord;\n"
        "uniform sampler2D texture;\n"
        "void main()\n"
        "{\n"
        "    gl_FragColor = texture2D(texture, fragmentTexCoord);\n"
        "}\n";

Tessellator Tessellator::draw(int width, int height, vector<jbyte> imgVector) {
    if (!drawing)
        std::cout << "Not drawing" << std::endl;

    GLuint vbo;
    glGenBuffers(1, &vbo);
    glBindBuffer(GL_ARRAY_BUFFER, vbo);

    glBufferData(GL_ARRAY_BUFFER, vertices.size() * sizeof(float) + texCoords.size() * sizeof(float), nullptr, GL_STATIC_DRAW);
    glBufferSubData(GL_ARRAY_BUFFER, 0, vertices.size() * sizeof(float), vertices.data());
    glBufferSubData(GL_ARRAY_BUFFER, vertices.size() * sizeof(float), texCoords.size() * sizeof(float), texCoords.data());
    glBindBuffer(GL_ARRAY_BUFFER, vbo);

    {
        GLuint vertexShader = glCreateShader(GL_VERTEX_SHADER);
        glShaderSource(vertexShader, 1, &vertexShaderSource, nullptr);
        glCompileShader(vertexShader);

        GLuint fragmentShader = glCreateShader(GL_FRAGMENT_SHADER);
        glShaderSource(fragmentShader, 1, &fragmentShaderSource, nullptr);
        glCompileShader(fragmentShader);

        GLuint shaderProgram = glCreateProgram();
        glAttachShader(shaderProgram, vertexShader);
        glAttachShader(shaderProgram, fragmentShader);

        glBindAttribLocation(shaderProgram, 0, "position");
        glBindAttribLocation(shaderProgram, 1, "texCoord");

        glLinkProgram(shaderProgram);
        glUseProgram(shaderProgram);

        GLuint textureID;
        glGenTextures(1, &textureID);
        glBindTexture(GL_TEXTURE_2D, textureID);

        int imageWidth, imageHeight, numChannels;
        unsigned char* imageData = stbi_load_from_memory(reinterpret_cast<const unsigned char*>(imgVector.data()), imgVector.size(), &imageWidth, &imageHeight, &numChannels, STBI_rgb_alpha);
        glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, imageWidth, imageHeight, 0, GL_RGBA, GL_UNSIGNED_BYTE, imageData);
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);

        GLint textureLoc = glGetUniformLocation(shaderProgram, "texture");
        glUniform1i(textureLoc, 0);

        glm::mat4 projectionMatrix = glm::ortho(0.0f, (float) width, (float) height, 0.0f, -1.0f, 1.0f);

        GLint projectionLoc = glGetUniformLocation(shaderProgram, "projection");
        glUniformMatrix4fv(projectionLoc, 1, GL_FALSE, glm::value_ptr(projectionMatrix));
    }

    glEnableVertexAttribArray(0);
    glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 0, nullptr);
    glEnableVertexAttribArray(1);
    glVertexAttribPointer(1, 2, GL_FLOAT, GL_FALSE, 0, reinterpret_cast<void*>(texCoords.size() * sizeof(float)));

    glDrawArrays(primitiveMode, 0, vertices.size());

    glDisableVertexAttribArray(0);
    glDisableVertexAttribArray(1);

    this->vertices.clear();
    this->texCoords.clear();
    this->drawing = false;
    return *this;
}

Tessellator Tessellator::vertex(double x, double y) {
    vertices.push_back((float) x);
    vertices.push_back((float) y);
    vertices.push_back(0.0f);
    return *this;
}

Tessellator Tessellator::tex(float x, float y) {
    texCoords.push_back(x);
    texCoords.push_back(y);

    return *this;
}

For tests i used this code:

auto tessellator = Tessellator::get();
    tessellator->begin(GL_TRIANGLES);

    tessellator->vertex(0, 0);
    tessellator->vertex(0, 100);
    tessellator->vertex(100, 0);

    tessellator->tex(0, 0);
    tessellator->tex(0, 1);
    tessellator->tex(1, 0);

    tessellator->draw(screenWidth, screenHeight, imgVector);

I use this code to draw a triangle with a texture

0

There are 0 best solutions below