1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166
| #pragma pack(push, 1)
// structure pour l'entete de fichier tga
typedef struct
{
uchar id_lenght; // size of image id
uchar colormap_type; // 1 is has a colormap
uchar image_type; // compression type
ushort cm_first_entry; // colormap origin
ushort cm_length; // colormap length
uchar cm_size; // colormap size
ushort x_origin; // bottom left x coord origin
ushort y_origin; // bottom left y coord origin
ushort width; // picture width (in pixels)
ushort height; // picture height (in pixels)
uchar pixel_depth; // bits per pixel: 8, 16, 24 or 32
uchar image_descriptor; // 24 bits = 0x00; 32 bits = 0x80
} tga_header_t;
#pragma pack(pop)
///////////////////////////////////////////////////////////////////////////////////////
// Chargement TGA
///////////////////////////////////////////////////////////////////////////////////////
/**
* @brief Creation d'un objet Image au format TGA
* @param pi Le pointeur image pour charger l'image
* @return L'image cree
*/
Image*
Chargeur::creerTGA(PointeurImage* pi)
{
// l'image a retourner
Image* im = 0;
// l'entete a creer
tga_header_t* header = (new tga_header_t);
void * entete = (void*)header;
// le colormap a creer si besoin PAS ENCORE OP
uchar *colormap = 0;
// le fichier a lire et sa taille
FILE *fp;
int taille;
// pointeur vers le debut des donnees(entete) et sur le debut des infos pixels
uchar* donnees = 0, *donneespixels = 0;
// ouverture du fichier pointe
fp = fopen (pi->getChemin(), "rb");
if (!fp)
{
fprintf (stderr, "erreur: fichier non trouve ou bloque \"%s\"!\n", pi->getChemin());
return 0;
}
// recuperation de la taille du fichier
fseek(fp, 0, SEEK_END);
taille = ftell(fp);
fseek(fp, 0, 0);
// allocation des donnees pour charger l'image
donnees = new uchar[ taille ];
if (!donnees)
{
fprintf (stderr, "erreur: pas assez de memoire pour charger l'image !\n");
return 0;
}
// lecture du fichier image d'une traite
fread( donnees, sizeof(uchar), taille, fp);
// fermeture du fichier
fclose (fp);
// on va lire l'entete jusqu'au donnees pixels, on incremente un des pointeur et l'autre restera au debut pour desallouer plus tard
donneespixels = donnees;
///////////////////// lecture de l'entete ////////////////////////////
header->id_lenght = (*(donneespixels++));
header->colormap_type = (*(donneespixels++));
header->image_type = (*(donneespixels++));
#ifdef MACOSX
// gestion du little endian sous Mac
ushort tempshort;
tempshort = (*(donneespixels++));
header->cm_first_entry = (*(donneespixels++));
header->cm_first_entry <<= 8;
header->cm_first_entry += tempshort;
tempshort = (*(donneespixels++));
header->cm_length = (*(donneespixels++));
header->cm_length <<= 8;
header->cm_length += tempshort;
#else
header->cm_first_entry = (*(donneespixels+=2));
header->cm_length = (*(donneespixels+=2));
#endif
header->cm_size = (*(donneespixels++));
#ifdef MACOSX
tempshort = (*(donneespixels++));
header->x_origin = (*(donneespixels++));
header->x_origin <<= 8;
header->x_origin += tempshort;
tempshort = (*(donneespixels++));
header->y_origin = (*(donneespixels++));
header->y_origin <<= 8;
header->y_origin += tempshort;
tempshort = (*(donneespixels++));
header->width = (*(donneespixels++));
header->width <<= 8;
header->width += tempshort;
tempshort = (*(donneespixels++));
header->height = (*(donneespixels++));
header->height <<= 8;
header->height += tempshort;
#else
header->x_origin = (*(donneespixels+=2));
header->y_origin = (*(donneespixels+=2));
header->width = (*(donneespixels+=2));
header->height = (*(donneespixels+=2));
#endif
header->pixel_depth = (*(donneespixels++));
header->image_descriptor = (*(donneespixels++));
// lecture du colormap si besoin
if (header->colormap_type)
{
// NOTE: color map is stored in BGR format
colormap = (donneespixels+=header->cm_length * (header->cm_size >> 3));
fprintf(stderr,"attention colormap %d\n",(*donneespixels));
}
#if defined DEBUG_FORMAT
fprintf(stderr, "%d %d %d %d\n",header->colormap_type, header->image_type, header->pixel_depth, header->image_descriptor);
#endif
// creation d'une image
im = new Image(header->width,header->height);
// passage des donnees utiles
im->setDonnees(donneespixels, donnees, entete, code_format_tga);
return im;
}
Image::~Image(void)
{
if (m_donnees != 0)
delete [] m_donnees;
if (m_entete != 0)
delete m_entete;
#if defined DEBUG_TAMPON_IMAGE
fprintf(stderr,"Destructeur Image\n");
#endif
} |