zoukankan      html  css  js  c++  java
  • 使用freetype来显示中文汉字和英文字符

    这里我们用到了freetype。进入官网http://savannah.nongnu.org/download/freetype/ 中下载最新的版本2.7的源代码和文件。freetype-2.7.tar.gz freetype-doc-2.7.tar.gz

    首先我们在使用官方提供的程序在pc上运行一下。需要安装zlib库。

    freetype-doc-2.7.tar.gz文件中的docus目录下的tutorial有一个example.c的源文件。

    example.c:

    /* example1.c                                                      */
    /*                                                                 */
    /* This small program shows how to print a rotated string with the */
    /* FreeType 2 library.                                             */
    
    
    #include <stdio.h>
    #include <string.h>
    #include <math.h>
    
    #include <ft2build.h>
    #include FT_FREETYPE_H
    
    
    #define WIDTH   80
    #define HEIGHT  80
    
    
    /* origin is the upper left corner */
    unsigned char image[HEIGHT][WIDTH];
    
    
    /* Replace this function with something useful. */
    
    void
    draw_bitmap( FT_Bitmap*  bitmap,
                 FT_Int      x,
                 FT_Int      y)
    {
      FT_Int  i, j, p, q;
      FT_Int  x_max = x + bitmap->width;
      FT_Int  y_max = y + bitmap->rows;
    
    
      for ( i = x, p = 0; i < x_max; i++, p++ )
      {
        for ( j = y, q = 0; j < y_max; j++, q++ )
        {
          if ( i < 0      || j < 0       ||
               i >= WIDTH || j >= HEIGHT )
            continue;
    
          image[j][i] |= bitmap->buffer[q * bitmap->width + p];
        }
      }
    }
    
    
    void
    show_image( void )
    {
      int  i, j;
    
    
      for ( i = 0; i < HEIGHT; i++ )
      {
        for ( j = 0; j < WIDTH; j++ )
          putchar( image[i][j] == 0 ? ' '
                                    : image[i][j] < 128 ? '+'
                                                        : '*' );
        putchar( '
    ' );
      }
    }
    
    
    int
    main( int     argc,
          char**  argv )
    {
      FT_Library    library;
      FT_Face       face;
    
      FT_GlyphSlot  slot;
      FT_Matrix     matrix;                 /* transformation matrix */
      FT_Vector     pen;                    /* untransformed origin  */
      FT_Error      error;
    
      char*         filename;
      char*         text;
    
      double        angle;
      int           target_height;
      int           n, num_chars;
    
    
      if ( argc != 3 )
      {
        fprintf ( stderr, "usage: %s font sample-text
    ", argv[0] );
        exit( 1 );
      }
    
      filename      = argv[1];                           /* first argument     */
      text          = argv[2];                           /* second argument    */
      num_chars     = strlen( text );
      angle         = ( 0.0 / 360 ) * 3.14159 * 2;      /* use 0 degrees  旋转     */
      target_height = HEIGHT;
    
      error = FT_Init_FreeType( &library );              /* initialize library */
      /* error handling omitted */
    
      error = FT_New_Face( library, filename, 0, &face );/* create face object */
      /* error handling omitted */
    
      /* use 50pt at 100dpi */
      error = FT_Set_Char_Size( face, 50 * 64, 0,
                                30, 0 );                /* set character size */
      /* error handling omitted */
    
      slot = face->glyph;
    
      /* set up matrix */
      matrix.xx = (FT_Fixed)( cos( angle ) * 0x10000L );
      matrix.xy = (FT_Fixed)(-sin( angle ) * 0x10000L );
      matrix.yx = (FT_Fixed)( sin( angle ) * 0x10000L );
      matrix.yy = (FT_Fixed)( cos( angle ) * 0x10000L );
    
      /* the pen position in 26.6 cartesian space coordinates; */
      /* start at (40,0) relative to the upper left corner  */
      pen.x = 0 * 64;
      pen.y = ( target_height - 40 ) * 64;
    
      for ( n = 0; n < num_chars; n++ )
      {
        /* set transformation */
        FT_Set_Transform( face, &matrix, &pen );
    
        /* load glyph image into the slot (erase previous one) */
        error = FT_Load_Char( face, text[n], FT_LOAD_RENDER );
        if ( error )
          continue;                 /* ignore errors */
    
        /* now, draw to our target surface (convert position) */
        draw_bitmap( &slot->bitmap,
                     slot->bitmap_left,
                     target_height - slot->bitmap_top );
    
        /* increment pen position */
        pen.x += slot->advance.x;
        pen.y += slot->advance.y;
      }
    
      show_image();
    
      FT_Done_Face    ( face );
      FT_Done_FreeType( library );
    
      return 0;
    }
    
    /* EOF */

     程序中把输出的字符打印在屏幕上,分辨率是640*480,从300,200 处开始显示.这里我为了便于查看就改为了80*80.从40,0处开始显示

     编译:

    gcc -o example1 example1.c -I /usr/local/include/freetype2/ -lfreetype -lm

     运行程序即可。

    arm:

    首先配置:

    ./configure --host=arm-linux
    make
    make DESTDIR=$PWD/tmp install

    将生成的文件拷贝到交叉编译器和开发板文件系统相应的位置。

    编译文件:

    arm-linux-gcc -o test main.c  -lfreetype -lm

    将test和字体文件拷贝到开发板中即可运行程序.

    源代码:

    #include <sys/types.h>
    #include <sys/stat.h>
    #include <sys/mman.h>
    #include <linux/fb.h>
    #include <stdio.h>
    #include <fcntl.h>
    #include <unistd.h>
    #include <string.h>
    #include <math.h>
    
    #include "show_font.h"
    #include <ft2build.h>
    #include FT_FREETYPE_H
    
    
    unsigned char *hzkmem;
    unsigned char *fbmem;
    unsigned int line_width;
    unsigned int pixel_width;
    
    struct fb_var_screeninfo var;
    
    void lcd_put_pixel( int x, int y, unsigned int color )
    {
        unsigned char *pen_8 = fbmem +y*line_width + x*pixel_width;
        unsigned short *pen_16;
        unsigned short *pen_32;
        unsigned char red,green,blue;
    
        pen_16 = (unsigned short *)pen_8;
        pen_32 = (unsigned short *)pen_8;
    
        switch( pixel_width*8 )
        {
        case 8:
            *pen_8 = color;
            break;
    
        case 16:
            /* 565 */
            red = (color>>16) & 0xff;
            green = (color>>8) & 0xff;
            blue = (color>>0) & 0xff;
            color = ((red>>3)<<11) | ((green>>2)<<5) |((blue>>3));
            *pen_16 = color;
            break;
    
        case 32:
            *pen_32 = color;
            break;
        default:
            printf("can't support %ddpp
    ",pixel_width*8 );
            break;
        }
    }
    
    void lcd_put_ascii( int x, int y, unsigned char c )
    {
        unsigned char *dots = (unsigned char *)&fontdata_8x16[c*16];
        int i,b;
        unsigned char byte;
    
        for( i=0; i< 16; i++ )
        {
            byte = dots[i];
            for( b=7;b>=0;b--)
            {
                if( byte & (1<<b))
                {
                    lcd_put_pixel(x+7-b,y+i, 0xffffff );
                }
                else
                {
                    lcd_put_pixel(x+7-b,y+i, 0x000000 );
                }
            }
        }
    
    }
    
    void lcd_put_chinese( int x, int y, unsigned char *c )
    {
        unsigned int area = c[0] - 0xa1;
        unsigned int where = c[1] - 0xa1;
        unsigned char *dots = hzkmem + (area*94+where)*32;
        unsigned char byte;
        int i,j,b;
        for( i=0; i<16; i++ )
        {
            for( j=0; j<2; j++ )
            {
                byte = dots[i*2+j];
                for( b=7; b>=0; b-- )
                {
                    if( byte & (1<<b) )
                        lcd_put_pixel(x+j*8+7-b,y+i, 0xffffff );
                    else
                        lcd_put_pixel(x+j*8+7-b,y+i, 0x000000 );
                }
            }
        }
    }
    
    void draw_bitmap( FT_Bitmap*  bitmap,
                 FT_Int      x,
                 FT_Int      y)
    {
      FT_Int  i, j, p, q;
      FT_Int  x_max = x + bitmap->width;
      FT_Int  y_max = y + bitmap->rows;
    
    
      for ( i = x, p = 0; i < x_max; i++, p++ )
      {
        for ( j = y, q = 0; j < y_max; j++, q++ )
        {
          if ( i < 0      || j < 0       ||
               i >= var.xres || j >= var.yres )
            continue;
    
          //image[j][i] |= bitmap->buffer[q * bitmap->width + p];
          lcd_put_pixel(i,j,bitmap->buffer[q * bitmap->width + p]);
        }
      }
    }
    
    int main( int argc, char **argv )
    {
        int hzk_fd;
        int fd_fb;
        struct fb_fix_screeninfo fix;
    
        int screen_size;
    
        FT_Library    library;
        FT_Error      error;
        FT_Face       face;
        FT_Matrix     matrix;                 /* transformation matrix */
        FT_Vector     pen;                    /* untransformed origin  */
    
        double        angle;
    
        wchar_t *chinese_char = L"周zhou";
    
    
    
    
        unsigned char str[]={0xd6,0xd0};
        struct stat hzk_stat;
    
    
        fd_fb = open("/dev/fb0",  O_RDWR );
        if( fd_fb<0 )
        {
            perror("oepn failed");
            return -1;
        }
    
        if( ioctl( fd_fb,  FBIOGET_VSCREENINFO, &var ) )
        {
            printf("can't get var
    ");
            return -1;
        }
    
        if( ioctl( fd_fb,  FBIOGET_FSCREENINFO, &fix ) )
        {
            printf("can't get fix
    ");
            return -1;
        }
        line_width = var.xres * var.bits_per_pixel / 8;
        pixel_width = var.bits_per_pixel / 8;
    
        screen_size = var.xres * var.yres * var.bits_per_pixel / 8;
        fbmem = (unsigned char *)mmap( NULL, screen_size,  PROT_READ | PROT_WRITE, MAP_SHARED,fd_fb,0 );
        if( fbmem == (unsigned char *)-1 )
        {
            printf("mmap is failed
    ");
            return -1;
        }
    
        hzk_fd = open("HZK16",  O_RDONLY );
        if( hzk_fd<0 )
        {
            printf("can't open hzk
    ");
            return -1;
        }
    
        if( fstat(hzk_fd, &hzk_stat))
        {
            printf("can't get fstat
    ");
            return -1;
        }
    
        hzkmem = (unsigned char *)mmap( NULL, hzk_stat.st_size,  PROT_READ, MAP_SHARED,hzk_fd,0 );
        if( hzkmem == (unsigned char *)-1 )
        {
            printf("mmap hzk is failed
    ");
            return -1;
        }
    
    
        memset( fbmem, 0, screen_size );
    
        lcd_put_ascii(var.xres/2,var.yres/2,'A' );
    
        printf("chinese code : %02x  %02x
    ", str[0],str[1]);
        lcd_put_chinese( var.xres/2 +8 ,var.yres/2, str );
    
        if( argc != 2 )
        {
            printf("Usage: %s  <font_file>
    ", argv[0]);
            return -1;
        }
    
        error = FT_Init_FreeType( &library );              /* initialize library */
        /* error handling omitted */
    
    
        error = FT_New_Face( library, argv[1], 0, &face ); /* create face object */
    
        /* use 50pt at 100dpi */
        error = FT_Set_Pixel_Sizes( face, 30, 0 );                /* set character size */
    
        angle         = ( 0.0 / 360 ) * 3.14159 * 2;      /* use 25 degrees     */
         /* set up matrix */
        matrix.xx = (FT_Fixed)( cos( angle ) * 0x10000L );
        matrix.xy = (FT_Fixed)(-sin( angle ) * 0x10000L );
        matrix.yx = (FT_Fixed)( sin( angle ) * 0x10000L );
        matrix.yy = (FT_Fixed)( cos( angle ) * 0x10000L );
    
        /* the pen position in 26.6 cartesian space coordinates; */
        /* start at (40,0) relative to the upper left corner  */
        pen.x = (var.xres/2+8+16) * 64;
        pen.y = ( var.yres/2 - 16 ) * 64;
    
        /* set transformation */
        FT_Set_Transform( face, &matrix, &pen );
    
        /* load glyph image into the slot (erase previous one) */
        error = FT_Load_Char( face, chinese_char[0], FT_LOAD_RENDER );
        if(error)
        {
            printf("FT_load_char error
    ");
            return -1;
        }
    
        draw_bitmap( &face->glyph->bitmap,
                     face->glyph->bitmap_left,
                     var.yres - face->glyph->bitmap_top );
    
    
        return 0;
    
    
    }

    sds

  • 相关阅读:
    DG Standby之REDO传输服务
    .NET缓存初探[转]
    大型门户网站架构分析[转]
    jquery.each读取json数据
    WebService简单验证:SoapHeader
    DIV上中下布局高度自适应的研究[转]
    C#随机数生成(Mersenne Twister)及最佳种子获得方法[保存]
    Yahoo给出的34条网站加速方法[转]
    Asp.net中基于Forms验证的角色验证授权[转]
    获取SWF参数传值
  • 原文地址:https://www.cnblogs.com/ynxf/p/6274067.html
Copyright © 2011-2022 走看看