begin process at 2010 02 10 00:41:08
  Trouver un code source :
 
dans
 
Accueil > Forum > 

C++ & C++ .NET

 > 

Divers

 > 

Divers

 > 

SDL image et masque


Derniers messages déposésPoser une question dans le forum ou lancer une discussion

SDL image et masque

dimanche 16 décembre 2007 à 16:56:26 | SDL image et masque

Timidouveg

Bonjour

Je poste pour la première fois ici
Je développe toutes sortes de petits programmes et aussi un projet de réalité virtuelle en C/C++ avec SDL/OpenGL et d'autres librairies que j'ajouterais par la suite. J'ai l'intention de poster des codes-sources sur ce site, mais avant j'aimerais vous les montrer et en discuter via ce forum, pour respecter le principe de ce site.

Aujourd'hui, je souhaite avoir votre avis sur un système d'images et de masques binaires codé en objet. Je voulais mettre une capture du résultat, mais je ne sais pas me servir de tout ça
Le système contient :
  1. un objet Image qui contient une SDL_Surface avec canal alpha, et un pointeur vers un masque binaire aux mêmes dimensions
  2. un objet Ecran qui hérite de Image et initialise l'écran (en tant qu'Image) et la fenêtre SDL
  3. un objet MasqueBin qui est constitué d'un tableau dynamique de booléens (binaire ) et ses dimensions
Je ne vous montre pas les objets Ecran et MasqueBin parce que leurs détails ne sont pas indispensables pour la partie dont je souhaite votre avis.
(Je ne sais pas mettre du code sur le forum)

Méthodes de Image :
static const Uint32 r_mask = 0x00FF0000;
static const Uint32 g_mask = 0x0000FF00;
static const Uint32 b_mask = 0x000000FF;
static const Uint32 a_mask = 0xFF000000;

/* Classe Image */
/* Constructeur d'Image avec paramètres */

Image::Image(char* fichier, int x, int y, int w, int h, MasqueBin *Masque)
{
// Chargement de l'image du fichier dans temp (en RAM)
SDL_Surface* temp = SDL_LoadBMP(fichier);
// Attribution d'une taille par défaut si valeur à 0
if ( w == 0 )
w = temp->w;
if ( h == 0 )
h = temp->w;

// Création de la surface final en VRAM ou en RAM
image = NULL;
image = SDL_CreateRGBSurface(SDL_HWSURFACE, w, h, 32, r_mask, g_mask, b_mask, a_mask); // en VRAM
if ( image == NULL ) // Si la mémoire video était saturée
image = SDL_CreateRGBSurface(SDL_SWSURFACE, w, h, 32, r_mask, g_mask, b_mask, a_mask); // en RAM
SDL_Rect R = {x,y,w,h};

// Copie de temp (en RAM) dans image (en VRAM ou en RAM)
SDL_BlitSurface(temp, &R, image, NULL);
// Suppression de temp : liberation de RAM
SDL_FreeSurface(temp);

// Attribution du masque, uniquement de mêmes dimensions
if ( Masque != NULL )
{
if ( Masque->w == w && Masque->h == h )
masque = Masque;
#ifdef _DEBUG
else
{
printf("ERREUR : Une image n'a pas pu recevoir le masque désiré,\n");
printf(" car ce dernier n'a pas les mêmes dimensions !\n");
printf(" image : %dx%d != masque : %dx%d\n",w, h, Masque->w, Masque->h);
}
#endif
}
}

/* Rendre invisible une couleur */
void Image::CouleurInvisible(int R, int V, int B)
{
Uint8 *imp = NULL;

// SDL_LockSurface(image);
#ifdef _DEBUG
if ( R <= 255 && R >= 0 && V <= 255 && V >= 0 && B <= 255 && B >= 0 )
{
#endif
for ( int y=0 ; y<image->h ; y++ )
{
imp = (Uint8 *)image->pixels + y * image->pitch;
for ( int x=0 ; x<image->w ; x++ )
{
if ( imp[0] == R && imp[1] == V && imp[2] == B )
imp[3] = 0;
imp += 4;
}
}
#ifdef _DEBUG
}
else
{
printf("ERREUR : Une image n'a pas pu recevoir de transparence,\n");
printf(" car la couleur spécifié %d:%d:%d n'existe pas !\n", R, V, B);
}
#endif
// SDL_UnlockSurface(image);
}

/* Effacer à la couleur et l'alpha désirés */
void Image::Effacer(int R, int V, int B, int A)
{
Uint8 *imp = NULL;

// SDL_LockSurface(image);
#ifdef _DEBUG
if ( R <= 255 && R >= 0 && V <= 255 && V >= 0 && B <= 255 && B >= 0 && A <= 255 && A >= 0 )
{
#endif
for ( int y=0 ; y<image->h ; y++ )
{
imp = (Uint8 *)image->pixels + y * image->pitch;
for ( int x=0 ; x<image->w ; x++ )
{
imp[0] = R;
imp[1] = V;
imp[2] = B;
imp[3] = A;
imp += 4;
}
}
#ifdef _DEBUG
}
else
{
printf("ERREUR : Une image n'a pas pu être effacé,\n");
printf(" car la couleur spécifié %d:%d:%d:%d n'existe pas !\n", R, V, B, A);
}
#endif
// SDL_UnlockSurface(image);
}

/* Dessiner l'image sur une autre */
// Optimisé ( environ 0.23 ms au dernier test, pas pu faire mieux)

void Image::Dessiner(Image* dest, int X, int Y, int W, int H)
{
Uint8 *dep = NULL, *imp = NULL;
int Xim = 0, Yim = 0;

// Ajustement des limites de la destination
if ( X < 0 )
{
Xim = -X;
X = 0;
}
if ( Y < 0 )
{
Yim = -Y;
Y = 0;
}
if ( X+W > dest->image->w ) W = dest->image->w - X;
if ( Y+H > dest->image->h ) H = dest->image->h - Y;
W -= Xim;
H -= Yim;

bool mask = true;
int i = 0;
// Dessin de l'image sur la destination
// SDL_LockSurface(dest->image);

for ( int y=0 ; y<H ; y++ )
{
dep = (Uint8 *)dest->image->pixels + (Y+y) * dest->image->pitch + X * 4;
imp = (Uint8 *)image->pixels + (Yim+y) * image->pitch + Xim * 4;
for ( int x=0 ; x<W ; x++ )
{
if ( dep[3] == 0 )
{
if ( masque != NULL )
mask = masque->b[i];
if ( mask )
{
if ( imp[3] != 0 )
{
dep[0] = imp[0];
dep[1] = imp[1];
dep[2] = imp[2];
dep[3] = imp[3];
}
}
dep += 4;
imp += 4;
}
i++;
}
}
// SDL_UnlockSurface(dest->image);
}

Je n'utilise pas les fonctions de dessin de SDL, je réécris les miennes sous formes de méthodes. Le dessin ne ce fait pas de l'écran vers l'utilisateur, mais à l'inverse. C'est à dire que l'ordinateur teste les du support sur lequel il doit dessiner et vérifie que son alpha est à 0. Si ce n'est pas le cas, c'est qu'il y a déjà quelque chose à cette endroit là, donc on ne dessine rien. Ce qui veut dire qu'on dessine d'abord les images devant et progressivement ceux qui suivent jusqu'au plus en arrière. Si une image est partiellement recouverte, elle sera partiellement dessiné, voir ignorée si totalement cachée.

J'ai tester la vitesse d'exécution de cette méthode et, à moins d'une erreur, c'est plus rapide que dessiner chaque images les unes sur les autres. Je pensais que tester les pixels était plus lent que directement dessiner sans rien vérifier, mais mes tests me disent l'inverse Si mes tests sont exacts alors je suis content, car mon but est d'optimiser la vitesse de calcul le plus possible, sans non plus trop mordre sur la mémoire.

Parcontre niveau gestion des images par rapport à la mémoire video. Je mets les images en mémoire video et après mes méthodes travaille dessus. J'ai mis en commentaire SDL_LockSurface() et SDL_UnlockSurface() parce que je ne suis pas sûr qu'ils soient utiles. Sans, ça fonctionne très bien, mais les images devrait être théoriquement en VRAM, à moins que ce ne soit pas le cas. Je ne comprends pas trop les Lock et Unlock dans SDL.



Cette discussion est classée dans : int, image, masque, sdl, imp


Répondre à ce message

Sujets en rapport avec ce message

Probleme, creation d'une class traitant sur SDL [ par kickbar ] Bonjour a tous, voila j'ai un petit souci, dans l'un de mes methodes, je charge la fenetre principale, je colle une image, et la mystere, a l'executio Problème fenêtre SDL sous Linux [ par Neofabiensama ] Bonjour,Je poste aujourd'hui car je suis à cours d'idée sur un problème de fenêtre SDL. Je travaille actuellement sur un projet de visualisation 2D d' Probleme en prog SDL.h [ par sieuzac ] Salut a tous.Je voudrez savoir pourquoi mon va plus vite au TEMP 2 qu'au TEMP 1#include #include #include #include /* surface qui sert à l'affich affiche une image sur mon interface [ par ribh ] pour afficher une image j'ai fait ce petit code: int main(int argc, char* argv[]) { QApplication app(argc, argv); QLabel label; //on donn LNK2005 et LNK1169, sur VS2008 avec SDL [ par Metalbobinou ] Bonjour, mes erreurs sont classiques d'apres google, mais je n'ai pas encore compris comment les resoudre... (meme en fouiannt un peu)... Je connais v Lecture d'un fichier Bmp (image en niveau de gris) et affichage des valeurs des pixels dans un vecteur [ par waffouna ] Salutj'ai vraiment besoin de vos aides.En fait, je suis un électronicienne et je travaille sur la reconnaissance de visage.Et dans le cadre de mon Pfe importation image en SDL [ par Richard94 ] Bonjour, voila j'ai un petit probleme en SDL, j'essaye d'importer une image format "xcf" en faisant IMG_load sous codeblocks, mais ça ne marche pas. P probleme thread/ SDL [ par ritchou42 ] salut tout le monde [^^happy7] voila je suis entrain de coder un gros projet pour mon école et j'ai un probleme au niveau de se code [code=cpp] int Correction de mon programme pour ecrire une image avec succés [ par ami2008 ] #include #include #include #include #define LARGEUR 256 #define HAUTEUR 256 int main() { //------------------------------------- // Déclaration Probleme sur les timer (SDL) [ par Loynis94 ] Bonjour, je viens de creer un petit programme censé reproduire une image qui rebondit de gauche à droite et de haut en bas. Mon programme marche au d


Nos sponsors


Sondage...

CalendriCode

Février 2010
LMMJVSD
1234567
891011121314
15161718192021
22232425262728

Consulter la suite du CalendriCode

 
Développement réalisé par Nicolas SOREL (Nix) avec l'aide de : Cyril DURAND et Emmanuel (EBArtSoft), Merci à Vincent pour ses précieux conseils.
CodeS-SourceS.com© Toute reproduction même partielle est interdite sauf accord écrit du Webmaster
CodeS-SourceS.com© est une marque déposée tous droits réservés

Google Coop CodeS-SourceS Google Coop CodeS-SourceS
Temps d'éxécution de la page : 0,312 sec (3)

Nous contacter | Annoncer sur CodeS-SourceS | Mentions légales