Conversion de fichier en fichier bmp

Contenu du snippet

Dans la même optique que ma source précédente, voici un programme pour faire des fichiers bmp en utilisant un fichier quelconque. Il prend en argument le nom du fichier à convertir et le nom du fichier de sotie (facultatif).

Source / Exemple :


#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <math.h>

int main(int argc, char *argv[])
{
	/* BMP header */
	char BM[2] = "BM"; //Magic number
	int FileSize; //Size of the BMP file
	short Creator1 = 0; //Unused
	short Creator2 = 0; //Unused
	int DataStart = 54; //Offset where the pixel array (bitmap data) can be found
	/*DIB header */
	int DIB = 40; //Number of bytes in the DIB header (from this point)
	int Width;
	int Height;
	short ColorPlanes = 1;
	short BitsPerPixel = 24;
	int Compression = 0; //BI_RGB, no pixel array compression used
	int DataSize; //Size of the raw data in the pixel array (including padding)
	int HorizontalResolution = 0;
	int VerticalResolution = 0;
	int ColorPalette = 0; //Number of colors in the palette
	int ImportantColors = 0; //0 means all colors are important
	/*Data start */
	
	char RawName[FILENAME_MAX], BmpName[FILENAME_MAX] = "bmp.bmp";
	if(argc > 1)
	{
		strcpy(RawName, argv[1]);
		if(argc > 2)
			strcpy(BmpName, argv[2]);
	}
	else
	{
		printf("bmp [RawFile]\n");
		return -1;
	}

	FILE *raw = fopen(RawName, "rb+");
	if(raw == NULL)
	{
		printf("File \"%s\" not found.\n", RawName);
		return -1;
	}
	FILE *bmp = fopen(BmpName, "wb");
	if(bmp == NULL)
	{
		printf("Can not create \"%s\".\n", BmpName);
		return -1;
	}
	fseek(raw, 0, SEEK_END);
	DataSize = ftell(raw); //donnees
	int tmp = DataSize;
	while(1)
	{
		if(tmp%3 == 0 && tmp%4 == 0 && (float)sqrt(tmp/3)-(int)sqrt(tmp/3) == 0 && (int)sqrt(tmp/3)%4 == 0) //Pour avoir un nombre de données multiple de 3 (RGB), aucun padding (multiple de 4), ainsi qu'un carre.
			break;
		else
			tmp++;
	}
	printf("Bits de plus : %d\n", tmp-DataSize);
	Width = sqrt(tmp/3);
	Height = sqrt(tmp/3);

	DataSize = tmp;
	FileSize = 54 + DataSize;//header + donnees
	printf("File Size = %d bits (%.0f kb)\n", FileSize, (float)FileSize/1024);
	
	fwrite(BM, 1, 2, bmp);
	fwrite(&FileSize, 4, 1, bmp);
	fwrite(&Creator1, 2, 1, bmp);
	fwrite(&Creator2, 2, 1, bmp);
	fwrite(&DataStart, 4, 1, bmp);
	fwrite(&DIB, 4, 1, bmp);
	fwrite(&Width, 4, 1, bmp);
	fwrite(&Height, 4, 1, bmp);
	fwrite(&ColorPlanes, 2, 1, bmp);
	fwrite(&BitsPerPixel, 2, 1, bmp);
	fwrite(&Compression, 4, 1, bmp);
	fwrite(&DataSize, 4, 1, bmp);
	fwrite(&HorizontalResolution, 4, 1, bmp);
	fwrite(&VerticalResolution, 4, 1, bmp);
	fwrite(&ColorPalette, 4, 1, bmp);
	fwrite(&ImportantColors, 4, 1, bmp);
	
	printf("Creating %s...\n", BmpName);
	char *p = calloc(DataSize,sizeof(char)); //calloc pour avoir des 0 (noir) pour les pixels supplementaires
	if(p == NULL)
	{
		printf("Dynamic memory allocation failed.\n");
		return -1;
	}
	fseek(raw, 0, SEEK_SET);
	fread(p, 1, DataSize, raw);
	fwrite(p, 1, DataSize, bmp);

	printf("%s created.\n", BmpName);
	free(p);
	
	fclose(raw);
	fclose(bmp);
}

Conclusion :


Les fichiers bmp sont étonnamment plus difficiles à gérer pour ce type d'opération qu'un wav, et donc ma source n'est pas des plus optimale, mais le tout fonctionne. Si jamais le fichier ne répond pas aux attentes fixées par le programme (aucun padding ainsi qu'une hauteur et largeur égale), il rajoute des octets jusqu'à ce que cette condition soie remplie. Les informations sur l'header du format bmp sont disponibles sur Wikipedia.

A voir également

Vous n'êtes pas encore membre ?

inscrivez-vous, c'est gratuit et ça prend moins d'une minute !

Les membres obtiennent plus de réponses que les utilisateurs anonymes.

Le fait d'être membre vous permet d'avoir un suivi détaillé de vos demandes et codes sources.

Le fait d'être membre vous permet d'avoir des options supplémentaires.