In questa pagina vediamo come è possibile, con un programma C, scrivere un file che contiene una immagine. Per prima cosa, i file immagini sono file come tutti gli altri, per cui possono venire aperti (in lettura oppure in scrittura) come un qualsiasi altro file. Quello che li rende diversi è solo il modo in cui sono organizzati, ossia il tipo di informazioni che contengono. Esistono numerosi modi di rappresentare una immagine su file, e ognuno di questi dà luogo a un differente formato. Formati esistenti sono per esempio: JPEG, GIF, BMP, PCX, PNG, TIFF, TGA, RAS/SUN, ICO, PBM, PPM, ecc.
In questa pagina vediamo il solo formato ``plain pbm'', che è il più facile da realizzare usando un programma C. Cominciamo quindi a leggere la specifica del formato pbm.
Per prima cosa, si tratta di un formato raster, ossia rappresenta una immagine pixel per pixel. Inoltre, si tratta di un formato per rappresentare solo immagini in bianco e nero. È quindi chiaro che, per ogni pixel dell'immagine che si va a rappresentare, il pixel può essere solo bianco o nero. In particolare, un file pbm è fatto come segue:
I primi due punti sono facili da interpretare: si scrive su file la stringa P1, poi la larghezza dell'immagine e poi l'altezza. Il terzo punto risulta subito chiaro se si disegna la griglia dei pixel, con le corrispondenti coordinate:
Il terzo punto della specifica dice semplicemente che i pixel devono apparire sul file come se venissero letti normalmente da sinistra a destra e dall'alto in basso. In altre parole, il file si ottiene leggendo i valori dei pixel come se fossero parole di un testo.
È quindi chiaro che si deve partire dal pixel in alto a sinistra, leggendo una riga per volta. Si deve quindi stampare prima il pixel di coordinate 0,h-1 poi 1,h-1 poi 2.h-2, ecc e solo quando la riga è finita si può passare alla coordinata y=h-2.
Supponiamo quindi di voler stampare una matrice in cui tutti i punti siano bianchi tranne quelli all'interno del rettangolo compreso fra i punti (10,10) e (40,20). Dal momento che dobbiamo stampare una riga per volta, e che il valore della coordinata y che indica la riga deve andare da h-1 a 0, il ciclo più esterno sarà:
for(y=h-1; y>=0; y--)
Per ogni riga, vanno stampati tutti i suoi punti, quindi occorre fare un secondo ciclo sulla coordinata x:
for(x=0; x<=w-1; x++)
Per ogni pixel, possiamo decidere se deve essere bianco o nero a seconda se si trova o meno all'interno del rettangolo. In particolare, il punto è nero solo se la sue coordinata x è compresa fra le x dei due punti estremi del rettangolo, e lo stesso per la y. Quindi, per ogni punto facciamo:
if( x>=10 && x<=40 && y>=10 && y<=20 ) fprintf(fd, "1\n"); else fprintf(fd, "0\n");
Il programma completo di stampa del rettangolo rettangolo.c è riportato qui sotto.
/* Scrive un rettangolo su file. */ #include<stdlib.h> #include<stdio.h> int main() { int w=200, h=100; FILE *fd; int x, y; /* apre il file */ fd=fopen("rettangolo.pbm", "w"); if( fd==NULL ) { perror("Errore in apertura del file"); exit(1); } /* scrive il rettangolo */ fprintf(fd, "P1\n"); fprintf(fd, "%d %d\n", w, h); for(y=h-1; y>=0; y--) for(x=0; x<=w-1; x++) if( x>=10 && x<=40 && y>=10 && y<=20 ) fprintf(fd, "1\n"); else fprintf(fd, "0\n"); /* chiude il file */ fclose(fd); return 0; }
L'immagine che viene prodotta da questo programma è riportata qui sotto.
|