/home/neoflo/smb4k/SERVEUR/Millie/trunk/src/ImageIO.cpp

Aller à la documentation de ce fichier.
00001 /******************************************************************************
00002  *       __    _    _   _       _       _   _____                             *
00003  *       | \  / |  | | | |     | |     | |  | ___|                            *
00004  *       |  \/  |  | | | |     | |     | |  | |_                              *
00005  *       |      |  | | | |     | |     | |  |  _|                             *
00006  *       | |\/| |  | | | |__   | |__   | |  | |__                             *
00007  *       |_|  |_|  |_| |____|  |____|  |_|  |____|                            *
00008  * __________________________________________________________________________ *
00009  *                 Multifunctional Library For Image Processing               *
00010  *                                                                            *
00011  *                                                                            *
00012  *                                                                            *
00013  *      (c) Copyright 2007 by Humbert Florent                                 *
00014  *                                                                            *
00015  *      This program is free software; you can redistribute it and/or modify  *
00016  *      it under the terms of the GNU General Public License as published by  *
00017  *      the Free Software Foundation; only version 2 of the License.          *
00018  *                                                                            *
00019  *      This program is distributed in the hope that it will be useful,       *
00020  *      but WITHOUT ANY WARRANTY; without even the implied warranty of        *
00021  *      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
00022  *      GNU General Public License for more details.                          *
00023  *                                                                            *
00024  *      You should have received a copy of the GNU General Public License     *
00025  *      along with this program; if not, write to the Free Software           *
00026  *      Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA             *
00027  *      02111-1307, USA.                                                      *
00028  ******************************************************************************/
00029 
00032 #ifndef _MILLIE_WITHOUT_SDL_
00033 #include <SDL/SDL.h>
00034 #endif
00035 
00036 #ifdef _MILLIE_WITH_SDLIMAGE_
00037 #include <SDL/SDL_image.h>
00038 #endif
00039 
00040 #include <iostream>
00041 
00042 #include "ImageIO.hpp"
00043 
00044 
00045 #define IMAGEIO_BLUE_COLOR 0
00046 #define IMAGEIO_RED_COLOR 1
00047 #define IMAGEIO_GREEN_COLOR 2
00048 
00049 using namespace Millie;
00050 
00051 #ifndef _MILLIE_WITHOUT_SDL_
00052 
00061 static Uint32 SDL_LireCouleurAux(const SDL_Surface* surface, int x, int y)
00062 {
00063   int bpp = surface->format->BytesPerPixel;
00064 
00065   Uint8 *p = (Uint8 *)surface->pixels + y * surface->pitch + x * bpp;
00066 
00067   switch(bpp)
00068   {
00069       case 1:
00070       return *p;
00071       case 2:
00072       return *(Uint16 *)p;
00073       case 3:
00074       if(SDL_BYTEORDER == SDL_BIG_ENDIAN)
00075         return p[0] << 16 | p[1] << 8 | p[2];
00076       else
00077         return p[0] | p[1] << 8 | p[2] << 16;
00078       case 4:
00079       return *(Uint32 *)p;
00080       default:
00081       return 0;
00082   }
00083 }
00084 
00085 
00096 static void SDL_LireCouleur(const SDL_Surface * surface, int x, int y, Uint8 * r, Uint8 * g, Uint8 * b)
00097 {
00098   if (x<0 | y<0 | x>=(surface->w) | y>=(surface->h))
00099   {
00100     *r = *g = *b = 0;
00101   }
00102 
00103   SDL_GetRGB(SDL_LireCouleurAux(surface, x, y), surface->format,
00104              (Uint8*)   r, (Uint8*) g, (Uint8*) b);
00105 
00106 }
00107 
00116 void SDL_EcrireCouleurAux(SDL_Surface* surface, int x, int y, Uint32 pixel)
00117 {
00118   int bpp = surface->format->BytesPerPixel;
00119   Uint8 *p = (Uint8 *)surface->pixels + y * surface->pitch + x * bpp;
00120 
00121 
00122   switch(bpp)
00123   {
00124       case 1:
00125       *p = pixel;
00126       break;
00127 
00128       case 2:
00129       *(Uint16 *)p = pixel;
00130       break;
00131 
00132       case 3:
00133       if(SDL_BYTEORDER == SDL_BIG_ENDIAN)
00134       {
00135         p[0] = (pixel >> 16) & 0xff;
00136         p[1] = (pixel >> 8) & 0xff;
00137         p[2] = pixel & 0xff;
00138       }
00139       else
00140       {
00141         p[0] = pixel & 0xff;
00142         p[1] = (pixel >> 8) & 0xff;
00143         p[2] = (pixel >> 16) & 0xff;
00144       }
00145       break;
00146 
00147       case 4:
00148       *(Uint32 *)p = pixel;
00149       break;
00150   }
00151 }
00152 
00163 void SDL_EcrireCouleur(SDL_Surface* surface, int x, int y, int r, int g, int b)
00164 {
00165   SDL_EcrireCouleurAux(surface, x, y,
00166                        SDL_MapRGB(surface->format, r, g, b));
00167 }
00168 
00174 static inline int floatTo0_255(float f)
00175 {
00176   return (int) (std::max(0.0f, std::min(255.0f, f)));
00177 }
00178 
00186 SDL_Surface*  imageToSDL_Surface32(const ImageRGB & imRGB)
00187 {
00188 
00189   int hauteur = imRGB.getHeight();
00190   int largeur = imRGB.getWidth();
00191 
00192 
00193   SDL_Surface* destination = SDL_CreateRGBSurface(SDL_HWSURFACE, largeur, hauteur,
00194                              32,
00195                              0xff0000,
00196                              0x00ff00,
00197                              0x0000ff,
00198                              0x000000);
00199   if(destination==NULL)
00200   {
00201     std::cerr<<"ImageIO::saveBMP Erreur Memoire"<<std::endl;
00202     throw std::bad_alloc();
00203   }
00204 
00205 
00206 
00207   for(int j = 0; j<hauteur;j++)
00208   {
00209     //std::cerr<<"Begin colonne"<<std::endl;
00210     for(int i = 0; i<largeur; i++)
00211     {
00212       SDL_EcrireCouleur(destination, i, j,
00213                         floatTo0_255(imRGB.getRedPixel(i,j)),
00214                         floatTo0_255(imRGB.getGreenPixel(i,j)),
00215                         floatTo0_255(imRGB.getBluePixel(i,j)));
00216     }
00217   }
00218 
00219   return destination;
00220 }
00221 
00232 SDL_Surface*  imagegrayToSDL_Surface32(const ImageGray & imGray, int color, bool all)
00233 {
00234 
00235   int hauteur = imGray.getHeight();
00236   int largeur = imGray.getWidth();
00237 
00238 
00239   SDL_Surface* destination = SDL_CreateRGBSurface(SDL_HWSURFACE, largeur, hauteur,
00240                              32,
00241                              0xff0000,
00242                              0x00ff00,
00243                              0x0000ff,
00244                              0x000000);
00245   if(destination==NULL)
00246   {
00247     std::cerr<<"ImageIO::saveBMP Erreur Memoire"<<std::endl;
00248     throw std::bad_alloc();
00249   }
00250 
00251   for(int j = 0; j<hauteur;j++)
00252   {
00253     //std::cerr<<"Begin colonne"<<std::endl;
00254     for(int i = 0; i<largeur; i++)
00255     {
00256       if(all)
00257       {
00258         SDL_EcrireCouleur(destination, i, j,
00259                           floatTo0_255(imGray.getPixel(i,j)),
00260                           floatTo0_255(imGray.getPixel(i,j)),
00261                           floatTo0_255(imGray.getPixel(i,j)));
00262       }
00263       else
00264       {
00265         if(color == IMAGEIO_BLUE_COLOR)
00266           SDL_EcrireCouleur(destination, i, j,
00267                             0,
00268                             0,
00269                             floatTo0_255(imGray.getPixel(i,j)));
00270         if(color == IMAGEIO_RED_COLOR)
00271           SDL_EcrireCouleur(destination, i, j,
00272                             floatTo0_255(imGray.getPixel(i,j)),
00273                             0,
00274                             0);
00275         if(color == IMAGEIO_BLUE_COLOR)
00276           SDL_EcrireCouleur(destination, i, j,
00277                             floatTo0_255(imGray.getPixel(i,j)),
00278                             0,
00279                             0);
00280 
00281       }
00282     }
00283   }
00284 
00285   return destination;
00286 }
00287 
00295 void sdl_SurfaceToImageRGB(ImageRGB & imRGB, const SDL_Surface*  origine)
00296 {
00297   if(origine==NULL)
00298     throw NullPointer("sdl_SurfaceToImageRGB");
00299 
00300   int hauteur = origine->h;
00301   int largeur = origine->w;
00302 
00303   imRGB.resize(largeur, hauteur);
00304 
00305 
00306   Uint8 r;
00307   Uint8 g;
00308   Uint8 b;
00309 
00310   for(int j = 0; j<hauteur;j++)
00311   {
00312     for(int i = 0; i<largeur; i++)
00313     {
00314       SDL_LireCouleur(origine, i, j, &r, &g, &b);
00315       imRGB.setRedPixel(i,j, (float) r);
00316       imRGB.setGreenPixel(i,j, (float) g);
00317       imRGB.setBluePixel(i,j, (float) b);
00318     }
00319   }
00320 }
00321 
00333 void sdl_SurfaceToImageGray(ImageGray & imGray, const SDL_Surface*  origine, int color)
00334 {
00335   if(origine==NULL)
00336     throw NullPointer("sdl_SurfaceToImageGray");
00337 
00338   if(color<0 || color>2)
00339     throw OutOfRange("sdl_SurfaceToImageGray : color range");
00340 
00341   int hauteur = origine->h;
00342   int largeur = origine->w;
00343 
00344   imGray.resize(largeur, hauteur);
00345 
00346   Uint8 r;
00347   Uint8 g;
00348   Uint8 b;
00349 
00350   for(int j = 0; j<hauteur;j++)
00351   {
00352     for(int i = 0; i<largeur; i++)
00353     {
00354       SDL_LireCouleur(origine, i, j, &r, &g, &b);
00355 
00356       if(color == IMAGEIO_RED_COLOR)
00357         imGray.setPixel(i,j, (float) r);
00358 
00359       if(color == IMAGEIO_GREEN_COLOR)
00360         imGray.setPixel(i,j, (float) g);
00361 
00362       if(color == IMAGEIO_BLUE_COLOR)
00363         imGray.setPixel(i,j, (float) b);
00364 
00365     }
00366   }
00367 
00368 }
00369 
00370 #endif
00371 
00372 
00381 void ImageIO::loadJPGComponent(ImageGray & im, const char * chemin, int color)
00382 {
00383 #ifdef _MILLIE_WITH_SDLIMAGE_
00384   if(chemin ==NULL)
00385     throw NullPointer("ImageIO::saveBMP");
00386 
00387   SDL_RWops *rwop = NULL;
00388   rwop=SDL_RWFromFile(chemin, "rb");
00389   if(rwop==NULL)
00390    throw IOException("LoadJPG");
00391 
00392   SDL_Surface* imageSDL = IMG_LoadJPG_RW(rwop);
00393 
00394   if(imageSDL==NULL)
00395   {
00396     std::cerr<<"Load JPG : Probleme de lecture fichier"<<std::endl;
00397     SDL_FreeRW(rwop);
00398     throw IOException("LoadJPG");
00399   }
00400 
00401 
00402   sdl_SurfaceToImageGray(im, imageSDL, color);
00403   SDL_FreeRW(rwop);
00404   SDL_FreeSurface(imageSDL);
00405 #else
00406  throw Exception("loadJPGComponent : Not yet implemented without SDL_Image");
00407 #endif
00408 }
00409 
00410 void ImageIO::loadJPGRedComponent(ImageGray & im, const char* chemin)
00411 {
00412   return ImageIO::loadJPGComponent(im, chemin, IMAGEIO_RED_COLOR);
00413 }
00414 
00415 void ImageIO::loadJPGGreenComponent(ImageGray & im, const char* chemin)
00416 {
00417   return ImageIO::loadJPGComponent(im, chemin, IMAGEIO_GREEN_COLOR);
00418 }
00419 
00420 void ImageIO::loadJPGBlueComponent(ImageGray & im, const char* chemin)
00421 {
00422   return ImageIO::loadJPGComponent(im, chemin, IMAGEIO_BLUE_COLOR);
00423 }
00424 
00425 void ImageIO::loadJPG(ImageRGB & imRGB, const char * chemin)
00426 {
00427 #ifdef _MILLIE_WITH_SDLIMAGE_
00428   if(chemin ==NULL)
00429     throw NullPointer("ImageIO::loadBMP");
00430 
00431   SDL_RWops *rwop = NULL;
00432   rwop=SDL_RWFromFile(chemin, "rb");
00433   if(rwop==NULL)
00434    throw IOException("LoadJPG");
00435 
00436   SDL_Surface* imageSDL = IMG_LoadJPG_RW(rwop);
00437 
00438   if(imageSDL==NULL)
00439   {
00440     std::cerr<<"Load JPG : Probleme de lecture fichier"<<std::endl;
00441     throw IOException("LoadJPG");
00442   }
00443 
00444   sdl_SurfaceToImageRGB(imRGB, imageSDL);
00445   SDL_FreeRW(rwop);
00446   SDL_FreeSurface(imageSDL);
00447 #else
00448  throw Exception("loadJPG : Not yet implemented without SDL_Image");
00449 #endif
00450 }
00451 
00462 void ImageIO::loadBMPComponent(ImageGray & im, const char* chemin, int color)
00463 {
00464 #ifndef _MILLIE_WITHOUT_SDL_
00465 if(chemin ==NULL)
00466     throw NullPointer("ImageIO::saveBMP");
00467 
00468   SDL_Surface* imageSDL =SDL_LoadBMP(chemin);
00469 
00470   if(imageSDL==NULL)
00471   {
00472     std::cerr<<"Load BMP : Probleme de lecture fichier"<<std::endl;
00473     throw IOException("LoadBMP");
00474   }
00475 
00476 
00477   sdl_SurfaceToImageGray(im, imageSDL, color);
00478   SDL_FreeSurface(imageSDL);
00479 #else
00480  throw Exception("loadBMP: Not yet implemented without SDL");
00481 #endif
00482 }
00483 
00484 void ImageIO::loadBMPGreenComponent(ImageGray & im, const char* chemin)
00485 {
00486   return ImageIO::loadBMPComponent(im, chemin, IMAGEIO_GREEN_COLOR);
00487 }
00488 
00489 void ImageIO::loadBMPBlueComponent(ImageGray & im, const char* chemin)
00490 {
00491   return ImageIO::loadBMPComponent(im, chemin, IMAGEIO_BLUE_COLOR);
00492 }
00493 
00494 void ImageIO::loadBMPRedComponent(ImageGray & im, const char* chemin)
00495 {
00496   return ImageIO::loadBMPComponent(im, chemin, IMAGEIO_RED_COLOR);
00497 }
00498 
00499 void       ImageIO::saveBMP(ImageGray & imGray, const char * chemin)
00500 {
00501 #ifndef _MILLIE_WITHOUT_SDL_
00502   if(chemin ==NULL)
00503     throw NullPointer("ImageIO::saveBMP");
00504 
00505   SDL_Surface* destination = imagegrayToSDL_Surface32(imGray,0 , true);
00506 
00507   if(SDL_SaveBMP(destination, chemin) == -1)
00508   {
00509     std::cerr<<"saveBMP : Erreur enregistrement"<<std::endl;
00510     throw IOException("saveBMP");
00511   }
00512 
00513   SDL_FreeSurface(destination);
00514 
00515   return;
00516 #else
00517  throw Exception("saveBMP : Not yet implemented without SDL");
00518 #endif
00519 }
00520 
00521 
00522 
00523 void ImageIO::loadBMP(ImageRGB & imRGB, const char * chemin)
00524 {
00525  #ifndef _MILLIE_WITHOUT_SDL_
00526   if(chemin ==NULL)
00527     throw NullPointer("ImageIO::loadBMP");
00528 
00529   SDL_Surface* imageSDL =SDL_LoadBMP(chemin);
00530 
00531   if(imageSDL==NULL)
00532   {
00533     std::cerr<<"Load BMP : Probleme de lecture fichier"<<std::endl;
00534     throw IOException("LoadBMP");
00535   }
00536 
00537   sdl_SurfaceToImageRGB(imRGB, imageSDL);
00538   SDL_FreeSurface(imageSDL);
00539   return;
00540 #else
00541  throw Exception("loadBMP : Not yet implemented without SDL");
00542 #endif
00543 }
00544 
00545 
00546 
00547 void ImageIO::saveBMP(ImageRGB & imRGB, const char * chemin)
00548 {
00549 #ifndef _MILLIE_WITHOUT_SDL_
00550   if(chemin ==NULL)
00551     throw NullPointer("ImageIO::saveBMP");
00552 
00553   SDL_Surface* destination = imageToSDL_Surface32(imRGB);
00554 
00555   if(SDL_SaveBMP(destination, chemin) == -1)
00556   {
00557     std::cerr<<"saveBMP : Erreur enregistrement"<<std::endl;
00558     throw IOException("saveBMP");
00559   }
00560 
00561   SDL_FreeSurface(destination);
00562 
00563   return;
00564 #else
00565  throw Exception("loadBMP : Not yet implemented without SDL");
00566 #endif
00567 }
00568 

Généré le Fri May 18 23:24:33 2007 pour Millie par  doxygen 1.5.1