]> git.tdb.fi Git - ttf2png.git/blobdiff - ttf2png.c
Improve glyph details output with -vv
[ttf2png.git] / ttf2png.c
index d9869bf173671caa4b6908f8f1cd357cb0e978ad..58b901666a282e4e1aee2805f1d53741a5a10568 100644 (file)
--- a/ttf2png.c
+++ b/ttf2png.c
@@ -66,6 +66,7 @@ typedef int bool;
 void usage(void);
 int convert_numeric_option(char, int);
 void convert_code_point_range(char, unsigned *, unsigned *);
+unsigned str_to_code_point(const char *, char **);
 void convert_size(char, unsigned *, unsigned *);
 unsigned round_to_pot(unsigned);
 void *alloc_image_data(size_t, size_t);
@@ -209,6 +210,12 @@ int main(int argc, char **argv)
        if(err)
                return 1;
 
+       if(!font.n_glyphs)
+       {
+               fprintf(stderr, "No glyphs found in the requested range\n");
+               return 1;
+       }
+
        if(pack)
                err = render_packed(&font, margin, padding);
        else
@@ -293,11 +300,11 @@ void convert_code_point_range(char opt, unsigned *begin, unsigned *end)
                return;
        }
 
-       value = strtol(optarg, &ptr, 0);
+       value = str_to_code_point(optarg, &ptr);
        if(value>0 && *ptr==',')
        {
                *begin = value;
-               value = strtol(ptr+1, &ptr, 0);
+               value = str_to_code_point(ptr+1, &ptr);
                if(value>0 && !*ptr)
                {
                        *end = value;
@@ -309,6 +316,44 @@ void convert_code_point_range(char opt, unsigned *begin, unsigned *end)
        exit(1);
 }
 
+unsigned str_to_code_point(const char *nptr, char **endptr)
+{
+       if(nptr[0]=='U' && nptr[1]=='+')
+               return strtoul(nptr+2, endptr, 16);
+       else if(nptr[0]&0x80)
+       {
+               unsigned bytes;
+               unsigned code;
+               unsigned i;
+
+               if(endptr)
+                       *endptr = (char *)nptr;
+
+               for(bytes=1; (bytes<4 && (nptr[0]&(0x80>>bytes))); ++bytes)
+                       if((nptr[bytes]&0xC0)!=0x80)
+                               return 0;
+               if(bytes<2)
+                       return 0;
+
+               code = nptr[0]&(0x3F>>bytes);
+               for(i=1; i<bytes; ++i)
+                       code = (code<<6)|(nptr[i]&0x3F);
+
+               if(endptr)
+                       *endptr = (char *)nptr+bytes;
+
+               return code;
+       }
+       else if(isdigit(nptr[0]))
+               return strtoul(nptr, endptr, 0);
+       else
+       {
+               if(endptr)
+                       *endptr = (char *)nptr+1;
+               return *nptr;
+       }
+}
+
 void convert_size(char opt, unsigned *width, unsigned *height)
 {
        int value;
@@ -421,7 +466,25 @@ int init_font(Font *font, FT_Face face, unsigned first, unsigned last, bool auto
                FT_Render_Glyph(face->glyph, FT_RENDER_MODE_NORMAL);
 
                if(verbose>=2)
-                       printf("  Char %u: glyph %u, size %dx%d\n", i, n, bmp->width, bmp->rows);
+               {
+                       printf("  Code point U+%04X", i);
+                       if(i>=0x20 && i<0x7F)
+                               printf(" (%c)", i);
+                       else if(i>=0xA0 && i<=0x10FFFF)
+                       {
+                               char utf8[5];
+                               unsigned bytes;
+
+                               for(bytes=2; i>>(1+bytes*5); ++bytes) ;
+                               for(j=0; j<bytes; ++j)
+                                       utf8[j] = 0x80 | ((i>>((bytes-j-1)*6))&0x3F);
+                               utf8[0] |= 0xF0<<(4-bytes);
+                               utf8[j] = 0;
+
+                               printf(" (%s)", utf8);
+                       }
+                       printf(": glyph %u, size %dx%d\n", n, bmp->width, bmp->rows);
+               }
 
                if(bmp->pixel_mode!=FT_PIXEL_MODE_GRAY)
                {