All my code is single-threaded at this time.
I have a texture manager that owns a collection of "texture collections" which in turn hold, "own" and manage all my game's textures as std::shared_ptr's. One collection is dedicated to my framebuffer textures. At initialization, it instantiates all my framebuffer textures, and later, a separate framebuffer object requests them all and stores its own std::shared_ptr references to these textures. I use this object in my deferred renderer. No problem so far: looking at the debug information in Visual Studio (2015), it shows two strong references (the one in the collection, and the one in the framebuffer object) per framebuffer texture; working as it should.
The problem arises when my window dimensions change. I listen for the WM_SIZE event, and upon a resize, my WndProc calls the following (again, on the references in my framebuffer texture collection, rather than my framebuffer object -- adhering to my ownership convention):
void PantheraTextureCollectionFramebuffer::Resize( unsigned int width, unsigned int height ) {
_textures["depth"].reset( new PantheraTexture( width, height, PantheraTextureFormat::Depth24,
PantheraTextureMinFilter::Nearest, PantheraTextureMagFilter::Nearest ) );
_textures["diffuseSpecular"].reset( new PantheraTexture( width, height, PantheraTextureFormat::RGBA8,
PantheraTextureMinFilter::Nearest, PantheraTextureMagFilter::Nearest ) );
_textures["normalParallax"].reset( new PantheraTexture( width, height, PantheraTextureFormat::RGBA8,
PantheraTextureMinFilter::Nearest, PantheraTextureMagFilter::Nearest ) );
_textures["position"].reset( new PantheraTexture( width, height, PantheraTextureFormat::RGB16F,
PantheraTextureMinFilter::Nearest, PantheraTextureMagFilter::Nearest ) );
_textures["uvMaterial"].reset( new PantheraTexture( width, height, PantheraTextureFormat::RGB16F,
PantheraTextureMinFilter::Nearest, PantheraTextureMagFilter::Nearest ) );
}
Which recreates all the textures with the new window dimensions. BUT, the std::shared_ptr's in the framebuffer object remain unchanged (apart from the ref counts for each texture, which drop to one). It seems I've fundamentally misjudged std::shared_ptr and its reset() method.
I've also tried reassigning using indirection, for example:
*_textures["depth"] = PantheraTexture(...)
which, aside from feeling unpleasantly hacky, doesn't call my texture objects' destructors and so OpenGL never frees the invalid textures.
I am stumped. I'd like to keep the texture objects immutable themselves, otherwise I'd probably implement an internal Resize method for them, leveraging glTexImage*D. How would you suggest going about maintaining continuity between my texture collection and my framebuffer object without resorting to that?
Thanks in advance.
Aucun commentaire:
Enregistrer un commentaire