1

I wrote this function to generate a texture in OpenGL. It correctly generates the texture I want which is a wooden box.

// This works
bool GenerateTextureFromFile(const int32_t mipMapLevel)
{
    int32_t width, height, channels;

    uint8_t* data = stbi_load(mProps.mPath.c_str(), &width, &height, &channels, 0);

    if (!data)
    {
        cout << "Failed to generate texture." << endl;

        return false;
    }

    mProps.mWidth = width;
    mProps.mHeight = height;

    Bind();

    glTexImage2D(GL_TEXTURE_2D,
                 mipMapLevel,
                 (uint32_t)mProps.mInternalFormat,
                 mProps.mWidth,
                 mProps.mHeight,
                 0,
                 (uint32_t)mProps.mImageFormat,
                 mProps.mDataType,
                 data);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, mProps.mWrapS);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, mProps.mWrapT);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, mProps.mFilterMin);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, mProps.mFilterMax);

    if (mipMapLevel)
        glGenerateMipmap(GL_TEXTURE_2D);    

    stbi_image_free(data);

    return true;
}

I would like to wrap that functionality into another function but when I do that glTexImage2D doesn't seem to generate the correct texture. Instead of the wooden box I get a black texture which indicates that the texture failed to generate. Am I losing data when I convert from uint8_t* to void*? What is the best way to do this?

// This fails to generate a texture
void SetDataNew(void* data, TextureProperties props, const int32_t mipMapLevel)
{
    mProps = std::move(props);

    Bind();

    glTexImage2D(GL_TEXTURE_2D,
                 mipMapLevel,
                 (uint32_t)mProps.mInternalFormat,
                 mProps.mWidth,
                 mProps.mHeight,
                 0,
                 (uint32_t)mProps.mImageFormat,
                 mProps.mDataType,
                 data);

    glTextureParameteri(mObjectID, GL_TEXTURE_MIN_FILTER, mProps.mFilterMin);
    glTextureParameteri(mObjectID, GL_TEXTURE_MAG_FILTER, mProps.mFilterMax);
    glTextureParameteri(mObjectID, GL_TEXTURE_WRAP_S, mProps.mWrapS);
    glTextureParameteri(mObjectID, GL_TEXTURE_WRAP_T, mProps.mWrapT);

    if (mipMapLevel)
        glGenerateMipmap(GL_TEXTURE_2D);
}

bool GenerateTextureFromFile(const int32_t mipMapLevel)
{
    int32_t width, height, channels;

    uint8_t* data = stbi_load(mProps.mPath.c_str(), &width, &height, &channels, 0);

    if (!data)
    {
        cout << "Failed to generate texture." << endl;

        return false;
    }

    mProps.mWidth = width;
    mProps.mHeight = height;

    SetDataNew(data, mProps, mipMapLevel);

    stbi_image_free(data);

    return true;
}

Here is my TextureProperties struct:

struct TextureProperties
{
    std::string mPath;
    uint32_t mWidth = 1;
    uint32_t mHeight = 1;
    TextureFormat mInternalFormat = TextureFormat::RGBA;
    TextureFormat mImageFormat = TextureFormat::RGBA;
    uint32_t mDataType = GL_UNSIGNED_BYTE;
    uint32_t mWrapS = GL_REPEAT;
    uint32_t mWrapT = GL_REPEAT;
    uint32_t mFilterMin = GL_LINEAR;
    uint32_t mFilterMax = GL_LINEAR;
};
Fate
  • 117
  • 1
  • 1
  • 4
  • You should not be losing anything from that pointer conversion. Does the move assignment for `TextureProperties` do anything funky? (One difference with your second is that it first copies `mProps` and then replaces it.) – molbdnilo Apr 13 '21 at 09:06
  • @molbdnilo I don't think so. It's just the default move constructor I edited the question to add my TextureProperties struct. – Fate Apr 13 '21 at 09:09
  • Why do you think the problem has anything to do with `data`? – user253751 Apr 13 '21 at 13:01

1 Answers1

0

The issue is here just realized accidentally put objectID instead of GL_TEXTURE_2D

glTextureParameteri(mObjectID, GL_TEXTURE_MIN_FILTER, mProps.mFilterMin);
glTextureParameteri(mObjectID, GL_TEXTURE_MAG_FILTER, mProps.mFilterMax);
glTextureParameteri(mObjectID, GL_TEXTURE_WRAP_S, mProps.mWrapS);
glTextureParameteri(mObjectID, GL_TEXTURE_WRAP_T, mProps.mWrapT);
Fate
  • 117
  • 1
  • 1
  • 4