In openGL. How do you copy part of a texture to another texture

c++, opengl, textures

Solution

If you have access to OpenGL 4.3 or the ARB_copy_image extension (or its older cousin, NV_copy_image), then you can use `glCopyImageSubData`.

Otherwise, you could use FBO blitting. You attach the source texture to an FBO, attach the destination texture to an FBO (possibly the same one, but if so, then obviously not to the same attachment point), set the read buffers and draw buffers for the FBOs to read from the source attachment and draw to the destination attachment, and then blit from one framebuffer to the other.

The trick you're trying to do doesn't work, BTW, because you never allocated storage for your new texture. `glTexSubImage` cannot be called for an image in a texture unless storage for that image has been allocated. This can be by a call to `glTexImage` or one of a number of other functions. The "SubImage" functions are all for uploading to existing storage, not for creating new storage.

Problem

I am trying to create a blank (white with no alpha) texture where I can load other textures and write part of them. I tried just having to get a portion of the texture, and using glTexSubImage2D to put it there it doesn't seem to work right. Anyone have any idea how to do this? What am i doing wrong? ``` int sourceTextWidth; int sourceTextHeight; int sourceFormat; int formatOffset = 0; //bind the texture glBindTexture( GL_TEXTURE_2D, textureID ); //get its params glGetTexLevelParameteriv(GL_TEXTURE_2D, 0, GL_TEXTURE_COMPONENTS, &sourceFormat); glGetTexLevelParameteriv(GL_TEXTURE_2D, 0, GL_TEXTURE_WIDTH, &sourceTextWidth); glGetTexLevelParameteriv(GL_TEXTURE_2D, 0, GL_TEXTURE_HEIGHT, &sourceTextHeight); switch (sourceFormat) { case GL_RGB: { formatOffset = 3; } break; case GL_RGBA: { formatOffset = 4; } break; } if (formatOffset == 0) { return false; } unsigned char * sourceData = (unsigned char *)malloc(sourceTextWidth * sourceTextHeight * formatOffset); glGetTexImage(GL_TEXTURE_2D, 0, GL_RGB, GL_UNSIGNED_BYTE, sourceData); glBindTexture( GL_TEXTURE_2D, m_currentTextureId ); unsigned char * destData = (unsigned char *)malloc(width * height * 3); glGetTexImage(GL_TEXTURE_2D, 0, GL_RGB, GL_UNSIGNED_BYTE, sourceData); for (int i = 0; i < height; ++i) { memcpy(&destData[(i * width * 3) ], &sourceData[((i + y) * sourceTextWidth * 3) + (x * 3)], width * 3); } //glDeleteTextures (1, m_currentTextureId); glBindTexture( GL_TEXTURE_2D, m_currentTextureId ); glTexSubImage2D( GL_TEXTURE_2D, 0, 0, 0, width, height, GL_RGB,GL_UNSIGNED_BYTE, destData ); free(destData); free(sourceData); ```

Original source

Related problems