Générer une transition entre deux textures avec SDL
Un article de Games Creators Network.
Sommaire |
[modifier] Principe
Le but de cet article est de montrer comment générer un dégradé entre deux textures.
Pour cela, on affiche la première texture à l'écran, on charge la seconde en mémoire et on modifie sa couche alpha pixel par pixel. Le but est de rendre la composant alpha de l'image égale à celle de l'image de transition.
[modifier] Aller plus loin: utilisation de ce principe dans un jeu 3d
Dans le cadre d'un moteur 3d supportant le multi-texturing, il est possible d'économiser le chargement en mémoire des textures de transition en générant ces transitions à la volée selon le principe appliqué dans cet article.
[modifier] Voir aussi
- Fondus enchaînés complexes avec SDL : programme assez similaire présentant le fonctionnement des fondus enchaînés avec SDL.
[modifier] Démo: générateur de dégradés
La fonction principale de ce programe GenereTransition prend quatre paramètres:
- avant: l'image de départ du dégradé
- apres: l'image d'arrivée du dégradé
- file_transition: le chemin indiquant l'image de transition
- filename: fichier dans lequel va être écrit la transition
#include <SDL/sdl.h> int GenereTransition( SDL_Surface *avant, SDL_Surface *apres, char *file_transition, char *filename); int main(int argc, char **argv) { SDL_Surface *screen, *fond1, *fond2; SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER); screen = SDL_SetVideoMode(256,256,32, SDL_HWSURFACE); SDL_WM_SetCaption("Fondu enchaîné avec SDL - Games Creators Network (http://www.games-creators.org/)",NULL); if(argc<5) { printf("Utilisation: transition_textures.exe <texture1.bmp> <texture2.bmp> <transition>.bmp> <rendu.bmp>\n"); SDL_Quit(); return 0; } fond1=SDL_LoadBMP(argv[1]); fond2=SDL_LoadBMP(argv[2]); GenereTransition(fond1, fond2, argv[3], argv[4]); printf( "La texture '%s' a été générée. Il s'agit de la texture de transition entre '%s' et '%s' selon le schéma '%s'.\n", argv[4], argv[1], argv[2], argv[3]); SDL_Quit(); return 0; } int GenereTransition( SDL_Surface *avant, SDL_Surface *apres, char *file_transition, char *filename) { SDL_Surface *copie, *transition; unsigned int rmask, gmask, bmask, amask, i; Uint32 temp, *pt, *pta; /* pointeurs vers les surfaces */ Uint8 r,g,b,a; Uint8 comp; /* Quelques vérifications pour éviter les principales sources de segfault */ if((!avant)||(!apres)) return 1; if(avant->w!=apres->w) return 1; if(avant->h!=apres->h) return 1; /* On copie la surface "avant" afin de pouvoir traviller dessus sans crainte */ #if SDL_BYTEORDER == SDL_BIG_ENDIAN rmask = 0xff000000; gmask = 0x00ff0000; bmask = 0x0000ff00; amask = 0x000000ff; #else rmask = 0x000000ff; gmask = 0x0000ff00; bmask = 0x00ff0000; amask = 0xff000000; #endif copie = SDL_CreateRGBSurface(SDL_SWSURFACE, 256, 256, 32, rmask, gmask, bmask, amask); SDL_BlitSurface(avant, NULL, copie, NULL); /* Chargement de la transition */ transition = SDL_LoadBMP(file_transition); transition = SDL_ConvertSurface(transition,copie->format,SDL_SWSURFACE|SDL_SRCALPHA); if(!transition) { SDL_FreeSurface(copie); return 1; } /* On fixe la transparence de la surface */ SDL_SetAlpha(copie, SDL_SRCALPHA, SDL_ALPHA_OPAQUE); /* Affiche fond */ SDL_BlitSurface(apres, NULL, SDL_GetVideoSurface(), NULL); /* Mise à jour de la couche alpha */ SDL_LockSurface(copie); SDL_LockSurface(transition); pt=((Uint32*)copie->pixels); pta=((Uint32*)transition->pixels); for(i=0;i<(copie->w*copie->h);i++) { SDL_GetRGBA(pt[i],copie->format,&r,&g,&b,&a); /* je ne récupère qu'une composante... c'est du niveau de gris! */ temp=pta[i]&transition->format->Rmask; temp=temp>>transition->format->Rshift; temp=temp<<transition->format->Rloss; comp=(Uint8)temp; pt[i]=SDL_MapRGBA(copie->format,r,g,b,comp); } SDL_UnlockSurface(transition); SDL_UnlockSurface(copie); /* On affiche la deuxième surface */ SDL_BlitSurface(copie, NULL, SDL_GetVideoSurface(), NULL); /* Inversion des tampons */ SDL_Flip(SDL_GetVideoSurface()); SDL_SaveBMP(SDL_GetVideoSurface(),filename); SDL_FreeSurface(transition); SDL_FreeSurface(copie); return 0; }
Cet outil s'utilise via la ligne de commande, la syntaxe est la suivante:
transition_textures.exe <texture1.bmp> <texture2.bmp> <transition.bmp> <rendu.bmp>
- texture1.bmp: image n°1 à partir de laquelle est générée le dégradé
- texture2.bmp: image n°2 à partir de laquelle est générée le dégradé
- transition.bmp: fichier de transition (image au format bitmap)
- rendu.bmp: nom du fichier dans lequel l'image générée sera sauvegardée.





