VC++ : Ecrire un fichier BMP

Ayla_21 Messages postés 9 Date d'inscription lundi 3 octobre 2005 Statut Membre Dernière intervention 15 novembre 2005 - 15 nov. 2005 à 15:55
mdkdo Messages postés 1 Date d'inscription dimanche 3 octobre 2004 Statut Membre Dernière intervention 14 février 2006 - 14 févr. 2006 à 22:45
Bonjour tout le monde,

Après avoir morflé sur la librairie jpeg, que j'ai fini par comprendre après moults désagréments. je m'attaque au format bmp.
Je dois écrire un fichier bmp, en m'inspirant largement du code de sebseb42, trouvé sur ce site j'ai concocté une mixture de code qui ne bugge pas et à bien l'air de créer un fichier bmp.

Mais quand je cherche à ouvrir le fichier généré, il me dit soit : "Aperçu non disponible" soit "Dessin échoué". Et là, impossible de trouver ce qu'il ne va pas.

Je pense que c'est une histoire de header de ficheir que je ne sois pas bien remplir : type BMP.
Je n'en sais rien. Si quelqu'un a une idée cela serait super cool

#include "iostream"
#include "fstream"
#include <string>
#include <stdio.h>
#include <sstream>
#include <stdlib.h>
#include <vector>
#include <list>
using namespace std;

// Type de compression
#define BI_RGB 0 // Aucune compression
#define BI_RLE8 1 // RLE 8 bpp
#define BI_RLE4 2 // RLE 4 bpp
#define BI_BITFIELDS 3 // Masque dans Palette

typedef struct s_rgb
{
unsigned char r;
unsigned char g;
unsigned char b;
unsigned char moy;


} t_rgb;

typedef struct s_bmp_fh
{
//short sType; // Deux caractères B et M
std::string sType;
int iSize; // Taille total du fichier
short sReserved1; // 0
short sReserved2; // 0
int iOffBits; // Offset des bits du bitmap dans le fichier


} t_bmp_fh;

typedef struct s_bmp_sh
{
int iSize; // Taille de cette structure en octets
int iWidth; // Largeur du bitmap en pixel
int iHeight; // Hauteur du bitmap en pixel
short sPlanes; // 1
short sBitCount; // Bits couleurs par pixel
int iCompression; // Schéma de compactage (0 pour aucun)
int iSizeImage; // Taille de l’image en octets (utile pour le compactage)
int iXpelsPerMeter; // Résolution horizontale en pixels par mètre
int iYpelsPerMeter; // Résolution verticale en pixels par mètre
int iClrUsed; // Nombre de couleurs utilisées dans l’image
int iClrImportant; // Nombre de couleurs importantes


} t_bmp_sh;

typedef struct s_bmp_header
{
t_bmp_fh first_header;
t_bmp_sh second_header;


} t_bmp_header;

typedef struct s_bmp
{
t_bmp_header header;
int width;
int width_useless;
int height;
t_rgb **data;
} t_bmp;

class cMatrice_Z
{
public :
int I;
int J;
float X;
float Y;
int NUM_PIX;
float Z_Buffer;
bool Allume_Pixel;
int ID_Face;
float XN;
float YN;
float ZN;
int R;
int V;
int B;
};


vector <cMatrice_Z> LMatrice_Z;
int main (char *filename, t_bmp *bmp)


{
float X01=1073.5, Y01 =221.4, Z01=25.5, Largeur=30.0, Hauteur =10.0, dirX=-0.5212401, dirY=0.8534101,dirZ=0.0 ,upX=0.0, upY=0.0,upZ=1.0 ;
float Echelle = 0.01;
float Resolution = 250;
float k = 2.5400000000000001; int u, NX=0, NY=0, card, i1, j1;
float DX,DY, X, Y;
int i, j;
int BytesPerLine;
FILE *fd;

//Calcul de DX et DY qui représentent la taille d'un PIXEL mais à l'échelle du terrain. Elle dépend de la taille du pixel en cm sur la photo remis à l'échelle du terrain


DX = 0.0254 /(Echelle * Resolution);
DY = DX;


//Calcul du nombre de colonne et de ligne qui dépendent de la largeur du plan de projection divisé par la taille d'un pixel. Idem pour la hauteur
NX = (int) (Largeur / DX);
NY = (int) (Hauteur / DX);
card = (NX* NY) ;
cMatrice_Z matZ;
int c =0;

for(u=0; u <card;u ++)
{

int NUM_PIX = u +1 ;
if (NUM_PIX == card)
{
i1 = NX;
j1 = NY;


X = i1 -0.5;
Y = j1 -0.5;
}
// calcule de i à de J


else


{
if ((NUM_PIX % NX) ==0) { c c + 1; i1 NX;
j1 = c;
X = i1 -0.5;
Y = j1 - 0.5; }
else {
j1 = (NUM_PIX / NX) + 1;
i1 = NUM_PIX%NX;
X = i1 -0.5;
Y = j1 - 0.5;
} }
matZ.I = i1;
matZ.J = j1;
matZ.X = X;
matZ.Y = Y;
matZ.R = 238;
matZ.V = 17;
matZ.B = 238;
matZ.NUM_PIX = NUM_PIX;
matZ.Allume_Pixel = false;
matZ.ID_Face = 0;
matZ.Z_Buffer = 0;
matZ.XN = 0;
matZ.YN = 0;
matZ.ZN = 0;
LMatrice_Z.push_back(matZ);
}//for z
if ((fd fopen("filename.bmp", "wb")) NULL)
{return 1;}

if ((NX * 3) % 4 == 0)
{ BytesPerLine = NX * 3; }
else
{ BytesPerLine = (NX * 3) + (4 - (NX * 3) % 4);}


//Affectation des valeurs de l'en-tête du fichier

bmp->header.first_header.sType = "BM";
bmp->header.first_header.iSize = sizeof(bmp->header.first_header) + sizeof(bmp->header.second_header) + BytesPerLine * NY; // 2 - 5
bmp->header.first_header.sReserved1 = 0; // 6 - 7
bmp->header.first_header.sReserved2 = 0; // 8 - 9
bmp->header.first_header.iOffBits = sizeof(bmp->header.first_header) + sizeof(bmp->header.second_header) ; // 10 - 13


bmp->header.second_header.iSize = sizeof(bmp->header.second_header); // 14 - 17
bmp->header.second_header.iWidth = NX; // 18 - 21
bmp->header.second_header.iHeight= NY; // 22 - 25
bmp->header.second_header.sPlanes = 1; // 26 - 27
bmp->header.second_header.sBitCount = 24; // 28 - 29
bmp->header.second_header.iCompression = BI_RGB; // 30 - 33
bmp->header.second_header.iSizeImage = 0; // 34 - 37
bmp->header.second_header.iXpelsPerMeter = 0; // 38 - 41
bmp->header.second_header.iYpelsPerMeter = 0; // 42 - 45
bmp->header.second_header.iClrUsed = 0; // 46 - 49
bmp->header.second_header.iClrImportant = 0; // 50 - 53


// Ecriture de l'en-tête du fichier

fwrite(&(bmp->header.first_header.sType), sizeof(short), 1, fd); // 0 - 1
fwrite(&(bmp->header.first_header.iSize), sizeof(int), 1, fd); // 2 - 5
fwrite(&(bmp->header.first_header.sReserved1), sizeof(short), 1, fd); // 6 - 7
fwrite(&(bmp->header.first_header.sReserved2), sizeof(short), 1, fd); // 8 - 9
fwrite(&(bmp->header.first_header.iOffBits), sizeof(int), 1, fd); // 10 - 13


fwrite(&(bmp->header.second_header.iSize), sizeof(int), 1, fd); // 14 - 17
fwrite(&(bmp->header.second_header.iWidth), sizeof(int), 1, fd); // 18 - 21
fwrite(&(bmp->header.second_header.iHeight), sizeof(int), 1, fd); // 22 - 25
fwrite(&(bmp->header.second_header.sPlanes), sizeof(short), 1, fd); // 26 - 27
fwrite(&(bmp->header.second_header.sBitCount), sizeof(short), 1, fd); // 28 - 29
fwrite(&(bmp->header.second_header.iCompression), sizeof(int), 1, fd); // 30 - 33
fwrite(&(bmp->header.second_header.iSizeImage), sizeof(int), 1, fd); // 34 - 37
fwrite(&(bmp->header.second_header.iXpelsPerMeter), sizeof(int), 1, fd); // 38 - 41
fwrite(&(bmp->header.second_header.iYpelsPerMeter), sizeof(int), 1, fd); // 42 - 45
fwrite(&(bmp->header.second_header.iClrUsed), sizeof(int), 1, fd); // 46 - 49
fwrite(&(bmp->header.second_header.iClrImportant), sizeof(int), 1, fd); // 50 - 53



int c25 = 0;
int Num_pixZ;


for ( j = 0; j < NY; j++)
{
for ( i = 0; i < NX; i++)
{
if (j==0)


{Num_pixZ = i + 1;}


else
{Num_pixZ = j*NX + (i+1);}
int r2 = LMatrice_Z[Num_pixZ-1].R;
int v2 = LMatrice_Z[Num_pixZ-1].V;
int b2 = LMatrice_Z[Num_pixZ-1].B;

fputc(r2, fd);
fputc(v2, fd);
fputc(b2, fd);
} }
fclose(fd);
return 0;
}


Ayla_21

2 réponses

BunoCS Messages postés 15472 Date d'inscription lundi 11 juillet 2005 Statut Modérateur Dernière intervention 25 mars 2024 103
15 nov. 2005 à 15:59
Regarde dans mes sources, il y a un loader BMP...

Buno
----------------------------------------
L'urgent est fait, l'impossible est en cours. Pour les miracles, prévoir un délai...
0
mdkdo Messages postés 1 Date d'inscription dimanche 3 octobre 2004 Statut Membre Dernière intervention 14 février 2006
14 févr. 2006 à 22:45
en effet moi aussi je cherche comment ecrire un bmp,j ai cree des appi de dessin

mais j ai juste des probleme avec l enregistrement,mais pas avec l ouvirture et affichage
j ai deja vu des appi de lecture et ecriture de bmp mais la manipulation de leur code est compliqué
dans tous les cas il n ya que trois structure en chaine comme suite dans le fichier:

BITMAPFILEHEADER
BITMAPINFOHEADER
RGBQUAD
puis les données du bitmap

alors si y de nouveau ?
Ouchen Mohamed devlop ,avec Microsoft Visual C++ 6.0 , win32 et MFC
mdkdo@caramail.com

et merci;
0
Rejoignez-nous