Bonjour, je me suis codé un petit programme permettant de récupérer la valeur des pixels contenus dans l'image seulement ce que j'ai fait fonctionne pour des images 32 bits mais pas pour des 24 bits.
Pourtant je fais bien un case selon le nb de bits et fait un traitement différent. J'ai beau cherché avec ddd et des print mais j'arrive pas a trouver ou cela coince. Au niveau des 24 bits lorsque je rempli ma matrice tout a l'air de bien se passer mais lorsque je veu afficher les valeurs j'ai une erreur de segmentation ... Quelqu'un pourrait-il m'aider svp
Je vous remercie d'avance je vous donne mon source ci dessous
#include<stdio.h>
#include<string.h>
#include<unistd.h>
#include<stdlib.h>
#define BF_TYPE 0x4D42
#pragma pack(push, 1)
#define BYTE unsigned char
///Header de fichier du BITMAP
typedef struct /**** BMP file header structure ****/
{
unsigned short bfType; /* Magic number for file 2 bytes */
unsigned int bfSize; /* Size of file 4 bytes */
unsigned short bfReserved1; /* Reserved 2 bytes */
unsigned short bfReserved2; /* ... 2 bytes */
unsigned int bfOffBits; /* Offset to bitmap data 4 bytes */
} BITMAPFILEHEADER;
///Header d'information du BITMAP
typedef struct /**** BMP file info structure ****/
{
unsigned int biSize; /* Size of info header 4 bytes */
unsigned int biWidth; /* Width of image 4 bytes */
unsigned int biHeight; /* Height of image 4 bytes*/
unsigned short biPlanes; /* Number of color planes */
unsigned short biBitCount; /* Number of bits per pixel */
unsigned int biCompression; /* Type of compression to use */
unsigned int biSizeImage; /* Size of image data */
unsigned int biXPelsPerMeter; /* X pixels per meter */
unsigned int biYPelsPerMeter; /* Y pixels per meter */
unsigned int biClrUsed; /* Number of colors used */
unsigned int biClrImportant; /* Number of important colors */
} BITMAPINFOHEADER;
//Couleur de palette colorimétrique
typedef struct
{
unsigned char rgbBlue;
unsigned char rgbGreen;
unsigned char rgbRed;
unsigned char rgbReserved;
} RGBQUAD;
///Pixels de BITMAP selon format
typedef struct
{
BYTE b;
BYTE g;
BYTE r;
} PIXEL_24;
typedef struct
{
BYTE b;
BYTE g;
BYTE r;
BYTE t;
} PIXEL_32;
typedef struct {
/*!
* Fichier image d'entree du textureur.
*/
const char* fichierImage;
} DescripteurTache ;
int main(int argc, char** argv)
{
BITMAPFILEHEADER fileheader; /* En-tete du fichier */
BITMAPINFOHEADER imageheader; /* En-tete de l'image */
FILE * fp; /* Pointeur de fichier */
BYTE * octets ;
BYTE * octets_courant; /* Pointeur parcourant les données image */
PIXEL_32 ** bitmaparray32;
PIXEL_24 ** bitmaparray24;
int i,j;
DescripteurTache tache;
/* Initialisation des valeurs par défauts */
tache.fichierImage = "bmp32.bmp";
char * filename = "test.bmp";
// traitement (simpliste) des arguments Unix
if (argc>=2) tache.fichierImage = argv[1];
/* On essaie d'ouvrir le fichier. On utilise le mode rb pour lire ce fichier binaire */
if ((fp = fopen(tache.fichierImage, "rb")) == NULL){
fprintf(stderr,"Impossible d'ouvrir le fichier demandé\n");
return (0);
}
/* On lit le nombre de données correspondant à l'en tête du fichier */
if (fread(&fileheader, sizeof(BITMAPFILEHEADER), 1, fp) < 1){
/* Couldn't read the file header - return NULL... */
fprintf(stderr,"Le fichier ne contient pas assez de données pour lire le header du fichier BMP\n");
fclose(fp);
return (0);
}
/* On s'assure que le fichier est bien du type BMP */
if (fileheader.bfType != BF_TYPE) /* Check for BM reversed... */
{
/* Not a bitmap file - return NULL... */
fprintf(stderr,"Le fichier spécifié n'est pas du type BMP\n");
fclose(fp);
return (0);
}
/* On lit le nombre de données correspondant à l'en tête du fichier */
if (fread(&imageheader, sizeof(BITMAPINFOHEADER), 1, fp) < 1){
/* Couldn't read the file header - return NULL... */
fprintf(stderr,"Le fichier ne contient pas assez de données pour lire le header de l'image BMP\n");
fclose(fp);
return (0);
}
/* On va se positionner au début des données propre à l'image */
fseek(fp, fileheader.bfOffBits, SEEK_SET );
/* On alloue de la mémoire de la taille des données images */
/* Le pointeur d'octets Octets pointe sur le premier
octet de l'espace attribué */
if ((octets = malloc(imageheader.biSizeImage*sizeof(BYTE))) == NULL){
/* Ne peut allouer de la mémoire - return NULL! */
fclose(fp);
return (0);
}
octets_courant = octets;
/* On lit les données images et les stocke dans l'espace alloué précédemment */
if(fread(octets,sizeof(BYTE),imageheader.biSizeImage,fp) < imageheader.biSizeImage){
/* Ne peut lire les données images */
free(octets);
fclose(fp);
return(0);
}
/* bitmaparray[i][j] */
/* i lignes */
/* j colonnes */
switch (imageheader.biBitCount) {
case 1:
break;
case 4:
break;
case 8:/*
break;
case 24:
/* Création des pointeurs formant la matrice */
bitmaparray24=(PIXEL_24**)malloc(imageheader.biHeight*sizeof(PIXEL_24));
for(i=0;i<imageheader.biWidth;i++){
bitmaparray24[i]=(PIXEL_24*)malloc(imageheader.biWidth*sizeof(PIXEL_24));
}
/* Remplissage */
for (i=imageheader.biHeight-1;i>=0;i--){
for(j=0;j<imageheader.biWidth;j++){
bitmaparray24[i][j].b=*octets_courant;
octets_courant+=1;
bitmaparray24[i][j].g=*octets_courant;
octets_courant+=1;
bitmaparray24[i][j].r=*octets_courant;
octets_courant+=1;
//printf("B:%d G:%d R:%d T:%d\n",bitmaparray[i][j].b,bitmaparray[i][j].g,bitmaparray[i][j].r,bitmaparray[i][j].t);
}
}
/* POUR TESTS */
for (i=imageheader.biHeight-1;i>=0;i--){
for(j=0;j<imageheader.biWidth;j++){
/* CAUSE une erreur
if(i==imageheader.biHeight-1)printf("B:%d G:%d R:%d \n",bitmaparray24[i][j].b,bitmaparray24[i][j].g,bitmaparray24[i][j].r); /*
*/
if(i==0)printf("B:%d G:%d R:%d \n",bitmaparray24[i][j].b,bitmaparray24[i][j].g,bitmaparray24[i][j].r);
}
}
break;
case 32:
/* Création des pointeurs formant la matrice */
bitmaparray32=(PIXEL_32**)malloc(imageheader.biHeight*sizeof(PIXEL_32));
for(i=0;i<imageheader.biWidth;i++){
bitmaparray32[i]=(PIXEL_32*)malloc(imageheader.biWidth*sizeof(PIXEL_32));
}
/* Remplissage */
for (i=imageheader.biHeight-1;i>=0;i--){
for(j=0;j<imageheader.biWidth;j++){
bitmaparray32[i][j].b=*octets_courant;
octets_courant+=1;
bitmaparray32[i][j].g=*octets_courant;
octets_courant+=1;
bitmaparray32[i][j].r=*octets_courant;
octets_courant+=1;
bitmaparray32[i][j].t=*octets_courant;
octets_courant+=1;
//printf("B:%d G:%d R:%d T:%d\n",bitmaparray[i][j].b,bitmaparray[i][j].g,bitmaparray[i][j].r,bitmaparray[i][j].t);
}
}
/* POUR TESTS */
for (i=imageheader.biHeight-1;i>=0;i--){
for(j=0;j<imageheader.biWidth;j++){
if(i==imageheader.biHeight-1)printf("B:%d G:%d R:%d \n",bitmaparray32[i][j].b,bitmaparray32[i][j].g,bitmaparray32[i][j].r);
//if(i==0)printf("B:%d G:%d R:%d \n",bitmaparray32[i][j].b,bitmaparray32[i][j].g,bitmaparray32[i][j].r);
}
}
break;
}
/* Libération de l'espace alloué */
free(octets);
printf("Magic Number For File : %d\n",fileheader.bfType);
printf("Size of File : %d bytes\n",fileheader.bfSize);
printf("Reserved 1 : %d \n",fileheader.bfReserved1);
printf("Reserved 2 : %d \n",fileheader.bfReserved2);
printf("Offset to bitmap data : %d\n",fileheader.bfOffBits);
printf("Size of info header : %d\n",imageheader.biSize);
printf("Largeur de l'image en pixel : %d\n",imageheader.biWidth);
printf("Hauteur de l'image en pixel : %d\n",imageheader.biHeight);
printf("Nombre de \"plan\" dans cet image: %d\n",imageheader.biPlanes);
printf("Nombre de bits par pixel : %d\n",imageheader.biBitCount);
printf("Type de compression utilisée : %d\n",imageheader.biCompression);
printf("Taille des données image : %d\n",imageheader.biSizeImage);
printf("X pixels par metre : %d\n",imageheader.biXPelsPerMeter);
printf("Y pixels par metre : %d\n",imageheader.biYPelsPerMeter);
printf("Nbr de couleurs utilisées : %d\n",imageheader.biClrUsed);
printf("Nbr d'importantes couleurs : %d\n",imageheader.biClrImportant);
/* TRAITEMENT SUR BITMAPARRAY */
/* SAUVEGARDE DANS UN AUTRE FICHIER */
/* On essaie d'ouvrir le fichier. On utilise le mode rb pour lire ce fichier binaire */
/* Création si inexistant */
if ((fp = fopen(filename, "wb")) == NULL){
fprintf(stderr,"Impossible d'ouvrir le fichier demandé\n");
return (0);
}
/* On recopie les données du header récupéré précédemment */
if (fwrite(&fileheader, sizeof(BITMAPFILEHEADER), 1, fp) < 1){
/* Couldn't read the file header - return NULL... */
fprintf(stderr,"Ecriture sur le fichier impossible\n");
fclose(fp);
return (0);
}
/* On écrit le nombre de données correspondant à l'en tête du fichier */
if (fwrite(&imageheader, sizeof(BITMAPINFOHEADER), 1, fp) < 1){
/* Couldn't read the file header - return NULL... */
fprintf(stderr,"Le fichier ne contient pas assez de données pour lire le header de l'image BMP\n");
fclose(fp);
return (0);
}
/* On alloue de la mémoire de la taille des données images */
/* Le pointeur d'octets Octets pointe sur le premier
octet de l'espace attribué */
if ((octets = malloc(imageheader.biSizeImage*sizeof(BYTE))) == NULL){
/* Ne peut allouer de la mémoire - return NULL! */
fclose(fp);
return (0);
}
octets_courant = octets;
printf("bip\n");
switch (imageheader.biBitCount) {
case 1:
break;
case 4:
break;
case 8:/*
if (fread(&grey,sizeof(unsigned char),1,fptr) != 1) {
fprintf(stderr,"Image read failed\n");
exit(-1);
}
if (gotindex) {
putchar(colourindex[grey].r);
putchar(colourindex[grey].g);
putchar(colourindex[grey].b);
} else {
putchar(grey);
}*/
break;
case 24:
printf("bap\n");
for (i=imageheader.biHeight-1;i>=0;i--){
for(j=0;j<imageheader.biWidth;j++){
*octets_courant=bitmaparray24[i][j].b;
octets_courant+=1;
*octets_courant=bitmaparray24[i][j].g;
octets_courant+=1;
*octets_courant=bitmaparray24[i][j].r;
octets_courant+=1;
//printf("B:%d G:%d R:%d T:%d\n",bitmaparray[i][j].b,bitmaparray[i][j].g,bitmaparray[i][j].r,bitmaparray[i][j].t);
}
}
/* On lit les données images et les stocke dans l'espace alloué précédemment */
if(fwrite(octets,sizeof(BYTE),imageheader.biSizeImage,fp) < imageheader.biSizeImage){
/* Ne peut lire les données images */
free(octets);
fclose(fp);
return(0);
}
break;
case 32:
for (i=imageheader.biHeight-1;i>=0;i--){
for(j=0;j<imageheader.biWidth;j++){
*octets_courant=bitmaparray32[i][j].b;
octets_courant+=1;
*octets_courant=bitmaparray32[i][j].g;
octets_courant+=1;
*octets_courant=bitmaparray32[i][j].r;
octets_courant+=1;
*octets_courant=bitmaparray32[i][j].t;
octets_courant+=1;
//printf("B:%d G:%d R:%d T:%d\n",bitmaparray[i][j].b,bitmaparray[i][j].g,bitmaparray[i][j].r,bitmaparray[i][j].t);
}
}
/* On lit les données images et les stocke dans l'espace alloué précédemment */
if(fwrite(octets,sizeof(BYTE),imageheader.biSizeImage,fp) < imageheader.biSizeImage){
/* Ne peut lire les données images */
free(octets);
fclose(fp);
return(0);
}
}
/* On libère l'espace alloué */
free(octets);
return(0);
}
#pragma pack (pop)