每帧多次调用 SDL_SetTextureColorMod 是否安全/可接受? [英] Is it safe/acceptable to call SDL_SetTextureColorMod every frame multiple times?

查看:41
本文介绍了每帧多次调用 SDL_SetTextureColorMod 是否安全/可接受?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

作为渲染除颜色以外的多个相同纹理的简单方法,我将一个纯白色圆圈加载到 SDL_Texture 中,然后调用 SDL_SetTextureColorMod() 给它我想制作圆圈的颜色.

如果纹理是单独的(示例 1),这一切都很好,但如果我共享 SDL_Texture 以便多个对象都引用它,则意味着 SDL_SetTextureColorMod() 必须在对象渲染纹理之前的每个渲染帧调用,因为它上次提供的颜色可能已被另一个对象更改(示例 2).

是否在每个渲染帧中调用 SDL_SetTextureColorMod(),因为可能相当多的对象共享一个纹理,会导致严重的性能问题吗?

需要它的原因是系统是使用具有基本引用计数的共享纹理功能设计的(我知道使用智能指针可能有更好的方法来做到这一点,但这不是这里讨论的主题).让每个对象拥有自己的 SDL_Texture 副本,这样它只需设置一次颜色(或在需要更改时)而不是每个渲染帧,这样会更好吗?>

示例 1:

SDL_Texture* tex1;SDL_Texture* tex2;SDL_Texture* tex3;...//所有 3 个实例都有自己的 SDL_Texture我的对象 A(tex1);我的对象 B(tex2);MyObject C(tex3);...//每个类只需要一次设置纹理颜色的调用

示例 2:

SDL_Texture* tex;...//所有 3 个实例共享 SDL_Texture我的对象 A(tex);MyObject B(tex);MyObject C(tex);...//必须在渲染前调用设置纹理的颜色//每个对象确保没有其他任何对象设置不同的颜色.//例如,如果绘制顺序是 A、B、C 并且颜色设置为不同//对于每个对象,然后在渲染 B 之前,它需要设置每一帧//颜色再次,否则它将具有 A 和相同的颜色//对于其他人

这也将扩展到 SDL_SetTextureAlphaMod()SDL_SetTextureBlendMode() 或其他类似功能

作为参考,我使用的是 SDL2.

更新:最初认为对函数的调用只是更新颜色混合标志.我做了一些更多的调查,这是部分正确的,可以在 - http://pastebin.com/pMjgVkmM 的函数中看到

但是,如果渲染器为 SetTextureColorMod() 分配了一个函数,这在大多数情况下似乎都是这种情况,那么它会映射到函数 'SW_SetTextureColorMod()' - http://pastebin.com/qYtxD0TH

这反过来调用 SDL_SetSurfaceColorMod() - http://pastebin.com/GrsVibAz一个>

我担心的是此时有一个潜在的 SDL_InvalidateMap 调用,我认为这会导致解除分配,尽管我不确定 - http://pastebin.com/r0HGJYHT

解决方案

SDL_SetTextureColorMod 不更新纹理纹素 - 它保存乘数颜色并提高 SDL_MODTEXTURE_COLOR 标志.对该纹理的后续 RenderCopy 将乘以固定颜色的纹素.

因为它不修改纹理,并且只是在纹理头中的一个小常量,所以在渲染帧中为相同的纹理多次设置它是完全可以的.克隆纹理会适得其反(更多的内存使用量,并可能由于更高的内存带宽压力而降低帧率).

As a simple way to render multiple textures that are the same other than color I load a plain white circle in to an SDL_Texture then just call SDL_SetTextureColorMod() giving it the color I want to make the circle.

This all works fine if the textures are individual (Example 1) but if I am sharing the SDL_Texture so that mutiple objects all reference it, it means that SDL_SetTextureColorMod() must be called every render frame before the object renders the texture since the color it gave last time may have been changed by another object (Example 2).

Is calling SDL_SetTextureColorMod() every render frame, for potentially quite a lot of objects sharing a texture, going to cause major performance issues?

The reason it is required is the system is designed using a shared texture functionality with basic reference counting (I understand that there are probably better ways to do this using smart pointers but that is not the topic for discussion here). Is it going to be better to just let each object have it's own copy of the SDL_Texture so it only has to set the color once (or whenever it needs to change) rather than every render frame?

Example 1:

SDL_Texture* tex1;
SDL_Texture* tex2;
SDL_Texture* tex3;
...
// All 3 instances have their own SDL_Texture
MyObject A(tex1);
MyObject B(tex2);
MyObject C(tex3);
...
// A call to set the color of the texture is only required once for each class

Example 2:

SDL_Texture* tex;
...
// All 3 instances share the SDL_Texture
MyObject A(tex);
MyObject B(tex);
MyObject C(tex);
...
// A call to set the color of the texture must be made before rendering 
// each object to ensure that any other object has not set a different color.
// E.g if the draw order was A, B, C and the color was set to be different
// for each object then before rendering B, each frame it would need to set 
// the color again otherwise it would have the color of A and the same 
// for the others    

Edit: This would also extend to SDL_SetTextureAlphaMod() and SDL_SetTextureBlendMode() or other similar functions

For reference I'm using SDL2.

Update: Originally it was thought that the call to the function is only updating a color blending flag. I have done some more investigation and this is partially correct which can be seen in the function in - http://pastebin.com/pMjgVkmM

However, if the renderer has a function assigned for SetTextureColorMod() which appears to be the case in most parts, then it mapped to a function 'SW_SetTextureColorMod()' - http://pastebin.com/qYtxD0TH

This in turn calls SDL_SetSurfaceColorMod() - http://pastebin.com/GrsVibAz

My concern here is at this point there is a potential call of SDL_InvalidateMap which I think can cause deallocation although I am not sure - http://pastebin.com/r0HGJYHT

解决方案

SDL_SetTextureColorMod doesn't update texture texels - it saves multiplier colour and raises SDL_MODTEXTURE_COLOR flag. Subsequent RenderCopy on that texture will multiply texels with fixed colour.

Since it don't modify texture, and just a little constant within texture header, it is completely ok to set it many times in render frame for the same texture. Cloning textures would be counterproductive (a lot more memory usage, and potentially lower framerate due to higher memory bandwidth pressure).

这篇关于每帧多次调用 SDL_SetTextureColorMod 是否安全/可接受?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆