Hi, all!
I use ogre-procedural and generate textures there. However when I destroy and create texture again the texture is not updated in the materials.
I need to fully reload application to update the texture in the materials however the texture itself has updated properly (checked by saving to file).
So the question is - how to force texture update in materials without texture name change, as the texture is in memory only?
The update is within editor and rare event. The texture is not dynamic.
Modifying texture on existing material Topic is solved
-
slapin
- Bronze Sponsor

- Posts: 339
- Joined: Fri May 23, 2025 5:04 pm
- x 24
Modifying texture on existing material
-
rpgplayerrobin
- Bugbear
- Posts: 803
- Joined: Wed Mar 18, 2009 3:03 am
- x 462
Re: Modifying texture on existing material
If I were you, I would just loop through all materials using it currently, add them to a list, create the new texture, and then apply it to the materials:
Code: Select all
std::string tmpTextureName = !!!;
// Fetch all materials using the texture name
std::vector<TextureUnitState> tmpTextureUnitStates;
ResourceManager::ResourceMapIterator tmpResourceIterator = MaterialManager::getSingleton().getResourceIterator();
while (tmpResourceIterator.hasMoreElements())
{
ResourcePtr tmpResourcePtr = tmpResourceIterator.getNext();
const Ogre::String& tmpResourceType = tmpResourcePtr->getCreator()->getResourceType();
if (tmpResourceType == "Material")
{
MaterialPtr tmpMaterialPtr = Ogre::static_pointer_cast<Material>(tmpResourcePtr);
if (tmpMaterialPtr)
{
for (unsigned short i = 0; i < tmpMaterialPtr->getNumTechniques(); i++)
{
Technique* tmpTechnique = tmpMaterialPtr->getTechnique(i);
for (unsigned short j = 0; j < tmpTechnique->getNumPasses(); j++)
{
Pass* tmpPass = tmpTechnique->getPass(j);
for (unsigned short n = 0; n < tmpPass->getNumTextureUnitStates(); n++)
{
TextureUnitState* tmpTextureUnitState = tmpPass->getTextureUnitState(n);
if (tmpTextureUnitState->getTextureName() == tmpTextureName)
{
tmpTextureUnitStates.push_back(tmpTextureUnitState);
// Also make sure to not use the texture anymore, so that it can be correctly destroyed if needed
tmpTextureUnitState->SetTextureName("white.png"); !!! Make sure this texture exists somewhere in your application
}
}
}
}
}
}
}
// Create your new texture
!!!
// Update the texture name if needed
tmpTextureName = !!!;
// Set the new texture to all materials again
for(size_t i = 0; i < tmpTextureUnitStates.size(); i++)
{
TextureUnitState* tmpTextureUnitState = tmpTextureUnitStates[i];
tmpTextureUnitState->SetTextureName(tmpTextureName);
}My project: https://imagindar.com/
-
slapin
- Bronze Sponsor

- Posts: 339
- Joined: Fri May 23, 2025 5:04 pm
- x 24
Re: Modifying texture on existing material
But can I do it without renaming? I have TexturePtr though... The material is only one at the moment...
-
paroj
- OGRE Team Member

- Posts: 2274
- Joined: Sun Mar 30, 2014 2:51 pm
- x 1239
Re: Modifying texture on existing material
you can blit from the new to the old texture:
https://ogrecave.github.io/ogre/api/lat ... f64bb1cb17
-
slapin
- Bronze Sponsor

- Posts: 339
- Joined: Fri May 23, 2025 5:04 pm
- x 24
Re: Modifying texture on existing material
I found another way.
Code: Select all
Ogre::String textureName =
"proceduralTextureTown" +
Ogre::StringConverter::toString(e.id());
Ogre::TexturePtr townTexture =
Ogre::TextureManager::getSingleton().getByName(
textureName);
if (townTexture) {
Ogre::TexturePtr newTownTexture =
colorAtlas.createTexture(textureName + "_copy");
newTownTexture->copyToTexture(townTexture);
Ogre::TextureManager::getSingleton().remove(
newTownTexture);
} else
Ogre::TexturePtr townTexture =
colorAtlas.createTexture(textureName);
And this works perfectly well, thanks!