source: vital-to8-sdk/gfx-tools/extract_font.c

Last change on this file was 1, checked in by svn, 6 years ago

Import initial

File size: 7.3 KB
RevLine 
[1]1#include "stdio.h"
2#include "stdlib.h"
3#include "math.h"
4
5/*
6
7        raw font converter from TGA image type 2 and 10
8
9*/
10
11typedef struct {
12   char  idlength;
13   char  colourmaptype;
14   char  datatypecode;
15   short int colourmaporigin;
16   short int colourmaplength;
17   char  colourmapdepth;
18   short int x_origin;
19   short int y_origin;
20   short width;
21   short height;
22   char  bitsperpixel;
23   char  imagedescriptor;
24} HEADER;
25
26typedef struct {
27   unsigned char r,g,b,a;
28} PIXEL;
29
30void MergeBytes(PIXEL *,unsigned char *,int);
31
32int main(int argc,char **argv)
33{
34   int n=0,i,j;
35   int bytes2read,skipover = 0;
36   unsigned char p[5];
37   FILE *fptr;
38   HEADER header;
39   PIXEL *pixels;
40
41   if (argc < 2) {
42      fprintf(stderr,"Usage: %s tgafile\n",argv[0]);
43      exit(-1);
44   }
45
46   /* Open the file */
47   if ((fptr = fopen(argv[1],"r")) == NULL) {
48      fprintf(stderr,"File open failed\n");
49      exit(-1);
50   }
51
52   /* Display the header fields */
53   header.idlength = fgetc(fptr);
54   fprintf(stderr,"ID length:         %d\n",header.idlength);
55   header.colourmaptype = fgetc(fptr);
56   fprintf(stderr,"Colourmap type:    %d\n",header.colourmaptype);
57   header.datatypecode = fgetc(fptr);
58   fprintf(stderr,"Image type:        %d\n",header.datatypecode);
59   fread(&header.colourmaporigin,2,1,fptr);
60   fprintf(stderr,"Colour map offset: %d\n",header.colourmaporigin);
61   fread(&header.colourmaplength,2,1,fptr);
62   fprintf(stderr,"Colour map length: %d\n",header.colourmaplength);
63   header.colourmapdepth = fgetc(fptr);
64   fprintf(stderr,"Colour map depth:  %d\n",header.colourmapdepth);
65   fread(&header.x_origin,2,1,fptr);
66   fprintf(stderr,"X origin:          %d\n",header.x_origin);
67   fread(&header.y_origin,2,1,fptr);
68   fprintf(stderr,"Y origin:          %d\n",header.y_origin);
69   fread(&header.width,2,1,fptr);
70   fprintf(stderr,"Width:             %d\n",header.width);
71   fread(&header.height,2,1,fptr);
72   fprintf(stderr,"Height:            %d\n",header.height);
73   header.bitsperpixel = fgetc(fptr);
74   fprintf(stderr,"Bits per pixel:    %d\n",header.bitsperpixel);
75   header.imagedescriptor = fgetc(fptr);
76   fprintf(stderr,"Descriptor:        %d\n",header.imagedescriptor);
77
78   /* Allocate space for the image */
79   if ((pixels = malloc(header.width*header.height*sizeof(PIXEL))) == NULL) {
80      fprintf(stderr,"malloc of image failed\n");
81      exit(-1);
82   }
83   for (i=0;i<header.width*header.height;i++) {
84      pixels[i].r = 0;
85      pixels[i].g = 0;
86      pixels[i].b = 0;
87      pixels[i].a = 0;
88   }
89
90   /* What can we handle */
91   if (header.datatypecode != 2 && header.datatypecode != 10) {
92      fprintf(stderr,"Can only handle image type 2 and 10\n");
93      exit(-1);
94   }
95   if (header.bitsperpixel != 16 &&
96       header.bitsperpixel != 24 && header.bitsperpixel != 32) {
97      fprintf(stderr,"Can only handle pixel depths of 16, 24, and 32\n");
98      exit(-1);
99   }
100   if (header.colourmaptype != 0 && header.colourmaptype != 1) {
101      fprintf(stderr,"Can only handle colour map types of 0 and 1\n");
102      exit(-1);
103   }
104
105   /* Skip over unnecessary stuff */
106   skipover += header.idlength;
107   skipover += header.colourmaptype * header.colourmaplength;
108   fprintf(stderr,"Skip over %d bytes\n",skipover);
109   fseek(fptr,skipover,SEEK_CUR);
110
111   /* Read the image */
112   bytes2read = header.bitsperpixel / 8;
113   while (n < header.width * header.height) {
114      if (header.datatypecode == 2) {                     /* Uncompressed */
115         if (fread(p,1,bytes2read,fptr) != bytes2read) {
116            fprintf(stderr,"Unexpected end of file at pixel %d\n",i);
117            exit(-1);
118         }
119         MergeBytes(&(pixels[n]),p,bytes2read);
120         n++;
121      } else if (header.datatypecode == 10) {             /* Compressed */
122         if (fread(p,1,bytes2read+1,fptr) != bytes2read+1) {
123            fprintf(stderr,"Unexpected end of file at pixel %d\n",i);
124            exit(-1);
125         }
126         j = p[0] & 0x7f;
127         MergeBytes(&(pixels[n]),&(p[1]),bytes2read);
128         n++;
129         if (p[0] & 0x80) {         /* RLE chunk */
130            for (i=0;i<j;i++) {
131               MergeBytes(&(pixels[n]),&(p[1]),bytes2read);
132               n++;
133            }
134         } else {                   /* Normal chunk */
135            for (i=0;i<j;i++) {
136               if (fread(p,1,bytes2read,fptr) != bytes2read) {
137                  fprintf(stderr,"Unexpected end of file at pixel %d\n",i);
138                  exit(-1);
139               }
140               MergeBytes(&(pixels[n]),p,bytes2read);
141               n++;
142            }
143         }
144      }
145   }
146   fclose(fptr);
147
148   fprintf(stderr,"[INFO] now in vm part ;) \n");
149   /* now count colors used */
150   int palette_24b[256];
151   int palette_to[16];
152   int col_num=1;
153   int val;
154   palette_24b[0]=(pixels[0].b<<16)|(pixels[0].g<<8)|(pixels[0].r);
155   for (i=1;i<header.height*header.width;i++) {
156      val=(pixels[i].b<<16)|(pixels[i].g<<8)|(pixels[i].r);
157      // does this color exists in palette     
158      for (j=0;j<col_num;j++) {
159        if (palette_24b[j]==val) break;
160      }
161      if (j==col_num) {
162         if (col_num==255) {
163            col_num=256;
164            fprintf(stderr,"[ERROR] too many colors (+256) !!!\n");
165            exit(-1);
166         }
167         palette_24b[col_num]=val;
168         col_num++;
169      }
170   }
171   fprintf(stderr,"[INFO] Number of unique colors %d\n",col_num);
172
173   if (col_num>16) {
174            fprintf(stderr,"[ERROR] too many colors %d\n",col_num);
175            exit(-1);
176   }
177
178        {
179                int col,row;
180                int nbcol,nbrow;
181                int subline,subcol;
182                int segment;
183               
184                nbcol=header.width/8;
185                nbrow=header.height/8;
186               
187                for (row=0;row<nbrow;row++) {
188                        for (col=0;col<nbcol;col++) {
189                                fprintf(stdout,"\tFCB\t");
190                                for (subline=0;subline<8;subline++) {
191                                        segment=0;
192                                        for (subcol=0;subcol<8;subcol++) {
193                                                segment=segment<<1;
194                                                if ((pixels[(row*8+subline)*header.width+(col*8)+subcol].g)>127) {
195                                                        segment|=1;
196                                                }
197                                        }
198                                        fprintf(stdout,"$%X",segment);
199                                        if (subline!=7) {
200                                                fprintf(stdout,",");
201                                        } else {
202                                                fprintf(stdout,"\n");
203                                        }
204                                }
205                        }
206                }
207        }
208
209}
210
211
212void
213output_tga(HEADER header,PIXEL *pixels) {
214   FILE *fptr;
215   int i;
216   /* Write the result as a uncompressed TGA */
217   if ((fptr = fopen("tgatest.tga","w")) == NULL) {
218      fprintf(stderr,"Failed to open outputfile\n");
219      exit(-1);
220   }
221   putc(0,fptr);
222   putc(0,fptr);
223   putc(2,fptr);                         /* uncompressed RGB */
224   putc(0,fptr); putc(0,fptr);
225   putc(0,fptr); putc(0,fptr);
226   putc(0,fptr);
227   putc(0,fptr); putc(0,fptr);           /* X origin */
228   putc(0,fptr); putc(0,fptr);           /* y origin */
229   putc((header.width & 0x00FF),fptr);
230   putc((header.width & 0xFF00) / 256,fptr);
231   putc((header.height & 0x00FF),fptr);
232   putc((header.height & 0xFF00) / 256,fptr);
233   putc(32,fptr);                        /* 24 bit bitmap */
234   putc(0,fptr);
235   for (i=0;i<header.height*header.width;i++) {
236      putc(pixels[i].b,fptr);
237      putc(pixels[i].g,fptr);
238      putc(pixels[i].r,fptr);
239      putc(pixels[i].a,fptr);
240   }
241   fclose(fptr);
242}
243
244void MergeBytes(PIXEL *pixel,unsigned char *p,int bytes)
245{
246   if (bytes == 4) {
247      pixel->r = p[2];
248      pixel->g = p[1];
249      pixel->b = p[0];
250      pixel->a = p[3];
251   } else if (bytes == 3) {
252      pixel->r = p[2];
253      pixel->g = p[1];
254      pixel->b = p[0];
255      pixel->a = 0;
256   } else if (bytes == 2) {
257      pixel->r = (p[1] & 0x7c) << 1;
258      pixel->g = ((p[1] & 0x03) << 6) | ((p[0] & 0xe0) >> 2);
259      pixel->b = (p[0] & 0x1f) << 3;
260      pixel->a = (p[1] & 0x80);
261   }
262}
263
Note: See TracBrowser for help on using the repository browser.