我尝试将多个纹理混合在一起并启用了抗锯齿功能,如果纹理没有旋转,它可以正常工作,但是当我旋转纹理时,抗锯齿会产生一个"边框"在纹理的边缘。以下是示例。
原始纹理,100x100px图像,中间有50x50px蓝色方块。
我将此纹理渲染两次:原样并旋转45度。它产生以下结果:
注意旋转纹理的灰色边框。在我看来,顶部的纹理应该与底部的纹理无缝融合,因为它们都包含相同颜色的像素。如果禁用了抗锯齿,那么纹理会按预期混合而没有任何边框,但显然我希望对旋转纹理进行消除锯齿。
有没有办法实现两者:抗锯齿纹理和无缝混合?
我使用SDL2和OpenGL进行渲染。以下是演示此效果的示例程序。
#include <assert.h>
#include <SDL2/SDL.h>
#include <SDL2/SDL_image.h>
void render(SDL_Renderer *renderer, SDL_Texture *tex) {
SDL_SetRenderDrawColor(renderer, 0, 0, 0, 0xFF);
SDL_RenderClear(renderer);
SDL_Rect dst_rect = { 0, 0, 100, 100 };
SDL_RenderCopyEx(renderer, tex, 0, &dst_rect,
0, 0, SDL_FLIP_NONE);
SDL_RenderCopyEx(renderer, tex, 0, &dst_rect,
45, 0, SDL_FLIP_NONE);
SDL_RenderPresent(renderer);
}
int main() {
SDL_Window *window;
SDL_Renderer *renderer;
SDL_Init(SDL_INIT_VIDEO);
SDL_CreateWindowAndRenderer(100, 100, SDL_WINDOW_OPENGL, &window, &renderer);
/* comment the following line for blended images */
SDL_SetHint(SDL_HINT_RENDER_SCALE_QUALITY, "best");
SDL_Texture *tex = IMG_LoadTexture(renderer, "./sample.png" );
assert(tex != 0);
SDL_SetTextureBlendMode(tex, SDL_BLENDMODE_BLEND);
render(renderer, tex);
SDL_Event event = { 0 };
while (1) {
if (SDL_PollEvent(&event) == 0) {
SDL_Delay(100);
continue;
}
if (event.type == SDL_QUIT) {
SDL_Quit();
break;
}
}
return 0;
}
编辑:我发现如果我在SDL_RenderCopyEx内部旋转纹理45度,它会添加不同颜色的半透明边框,请参见下图。
请注意旋转图像边缘的颜色变化情况。
答案 0 :(得分:1)
我发现的工作解决方案是用几乎透明的相同颜色的像素填充图像的透明部分。参考图片:
该图片中的“透明”颜色为0x0187ceeb(ARGB)。然后按预期生成混合图像:
此解决方法的一些详细信息如下所述:http://www.saschahlusiak.de/2012/10/opengl-antialiasing-in-android-with-transparent-textures/