假设我们有一个 32 位的 PNG 文件,其中有一些幽灵般的/无形的角色,它是以半透明的方式绘制的。它并不是在每个地方都同样透明,因此在将其加载到表面时我们需要每个像素的 alpha 信息。
对于淡入/淡出,设置整个表面的alpha值是一个好方法;但在这种情况下不是,因为表面已经具有每个像素的信息,而 SDL 不会将两者结合起来。
什么是有效的解决方法(而不是要求艺术家为角色提供一些很棒的淡入/淡出动画)?
最佳答案
我认为获得所需结果的最简单方法是首先加载包含角色 Sprite 的 source
表面,然后,为幽灵的每个实例创建一个 working
表面的拷贝。您要做的是,每次实例的 alpha 值发生变化时,SDL_BlitSurface
( doc) 您的source
进入您的working
复制并应用您的透明度(您可能应该将其保持为 0 到 1 之间的 float ),然后将您的透明度应用于每个像素的 alpha channel 。
在 32 位表面的情况下,假设您最初加载了 source
并分配了 working
SDL_Surface
,您可能可以做一些事情行:
SDL_BlitSurface(source, NULL, working, NULL);
if(SDL_MUSTLOCK(working))
{
if(SDL_LockSurface(working) < 0)
{
return -1;
}
}
Uint8 * pixels = (Uint8 *)working->pixels;
pitch_padding = (working->pitch - (4 * working->w));
pixels += 3; // Big Endian will have an offset of 0, otherwise it's 3 (R, G and B)
for(unsigned int row = 0; row < working->h; ++row)
{
for(unsigned int col = 0; col < working->w; ++col)
{
*pixels = (Uint8)(*pixels * character_transparency); // Could be optimized but probably not worth it
pixels += 4;
}
pixels += pitch_padding;
}
if(SDL_MUSTLOCK(working))
{
SDL_UnlockSurface(working);
}
此代码的灵感来自 SDL_gfx
( here ),但如果您只这样做,我不会为此链接库。
关于C++/SDL : Fading out a surface already having per-pixel alpha information,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16815699/