Advertisement
Guest User

estar

a guest
Dec 1st, 2007
179
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 21.77 KB | None | 0 0
  1. diff -Naurp cairo-1.5.2-old/src/cairo-ft-font.c cairo-1.5.2/src/cairo-ft-font.c
  2. --- cairo-1.5.2-old/src/cairo-ft-font.c 2007-10-31 06:02:55.000000000 +0100
  3. +++ cairo-1.5.2/src/cairo-ft-font.c 2007-12-01 10:14:45.000000000 +0100
  4.  -55,6 +55,8 @@
  5.  #include FT_SYNTHESIS_H
  6.  #endif
  7.  
  8. +#include FT_LCD_FILTER_H
  9. +
  10.  #define DOUBLE_TO_26_6(d) ((FT_F26Dot6)((d) * 64.0))
  11.  #define DOUBLE_FROM_26_6(t) ((double)(t) / 64.0)
  12.  #define DOUBLE_TO_16_16(d) ((FT_Fixed)((d) * 65536.0))
  13.  -707,23 +709,300 @@ _cairo_ft_unscaled_font_set_scale (cairo
  14.      return CAIRO_STATUS_SUCCESS;
  15.  }
  16.  
  17. -/* Empirically-derived subpixel filtering values thanks to Keith
  18. - * Packard and libXft. */
  19. -static const int    filters[3][3] = {
  20. -    /* red */
  21. -#if 0
  22. -    {    65538*4/7,65538*2/7,65538*1/7 },
  23. -    /* green */
  24. -    {    65536*1/4, 65536*2/4, 65537*1/4 },
  25. -    /* blue */
  26. -    {    65538*1/7,65538*2/7,65538*4/7 },
  27. +/* we sometimes need to convert the glyph bitmap in a FT_GlyphSlot
  28. + * into a different format. For example, we want to convert a
  29. + * FT_PIXEL_MODE_LCD or FT_PIXEL_MODE_LCD_V bitmap into a 32-bit
  30. + * ARGB or ABGR bitmap.
  31. + *
  32. + * this function prepares a target descriptor for this operation.
  33. + *
  34. + * input :: target bitmap descriptor. The function will set its
  35. + *          'width', 'rows' and 'pitch' fields, and only these
  36. + *
  37. + * slot  :: the glyph slot containing the source bitmap. this
  38. + *          function assumes that slot->format == FT_GLYPH_FORMAT_BITMAP
  39. + *
  40. + * mode  :: the requested final rendering mode. supported values are
  41. + *          MONO, NORMAL (i.e. gray), LCD and LCD_V
  42. + *
  43. + * the function returns the size in bytes of the corresponding buffer,
  44. + * it's up to the caller to allocate the corresponding memory block
  45. + * before calling _fill_xrender_bitmap
  46. + *
  47. + * it also returns -1 in case of error (e.g. incompatible arguments,
  48. + * like trying to convert a gray bitmap into a monochrome one)
  49. + */
  50. +static int
  51. +_compute_xrender_bitmap_size( FT_Bitmap*      target,
  52. +                              FT_GlyphSlot    slot,
  53. +                              FT_Render_Mode  mode )
  54. +{
  55. +    FT_Bitmap*  ftbit;
  56. +    int         width, height, pitch;
  57. +
  58. +    if ( slot->format != FT_GLYPH_FORMAT_BITMAP )
  59. +        return -1;
  60. +
  61. +    // compute the size of the final bitmap
  62. +    ftbit  = &slot->bitmap;
  63. +
  64. +    width  = ftbit->width;
  65. +    height = ftbit->rows;
  66. +    pitch  = (width+3) & ~3;
  67. +
  68. +    switch ( ftbit->pixel_mode )
  69. +    {
  70. +    case FT_PIXEL_MODE_MONO:
  71. +        if ( mode == FT_RENDER_MODE_MONO )
  72. +        {
  73. +          pitch = (((width+31) & ~31) >> 3);
  74. +          break;
  75. +        }
  76. +        /* fall-through */
  77. +
  78. +    case FT_PIXEL_MODE_GRAY:
  79. +        if ( mode == FT_RENDER_MODE_LCD   ||
  80. +            mode == FT_RENDER_MODE_LCD_V )
  81. +        {
  82. +            /* each pixel is replicated into a 32-bit ARGB value */
  83. +            pitch = width*4;
  84. +        }
  85. +        break;
  86. +
  87. +    case FT_PIXEL_MODE_LCD:
  88. +        if ( mode != FT_RENDER_MODE_LCD )
  89. +            return -1;
  90. +
  91. +      /* horz pixel triplets are packed into 32-bit ARGB values */
  92. +      width   /= 3;
  93. +      pitch    = width*4;
  94. +      break;
  95. +
  96. +    case FT_PIXEL_MODE_LCD_V:
  97. +        if ( mode != FT_RENDER_MODE_LCD_V )
  98. +            return -1;
  99. +
  100. +        /* vert pixel triplets are packed into 32-bit ARGB values */
  101. +        height  /= 3;
  102. +        pitch    = width*4;
  103. +        break;
  104. +
  105. +    default:  /* unsupported source format */
  106. +        return -1;
  107. +    }
  108. +
  109. +    target->width  = width;
  110. +    target->rows   = height;
  111. +    target->pitch  = pitch;
  112. +    target->buffer = NULL;
  113. +
  114. +    return pitch * height;
  115. +}
  116. +
  117. +/* this functions converts the glyph bitmap found in a FT_GlyphSlot
  118. + * into a different format (see _compute_xrender_bitmap_size)
  119. + *
  120. + * you should call this function after _compute_xrender_bitmap_size
  121. + *
  122. + * target :: target bitmap descriptor. Note that its 'buffer' pointer
  123. + *           must point to memory allocated by the caller
  124. + *
  125. + * slot   :: the glyph slot containing the source bitmap
  126. + *
  127. + * mode   :: the requested final rendering mode
  128. + *
  129. + * bgr    :: boolean, set if BGR or VBGR pixel ordering is needed
  130. + */
  131. +static void
  132. +_fill_xrender_bitmap( FT_Bitmap*      target,
  133. +                      FT_GlyphSlot    slot,
  134. +                      FT_Render_Mode  mode,
  135. +                      int             bgr )
  136. +{
  137. +    FT_Bitmap*   ftbit = &slot->bitmap;
  138. +    unsigned char*   srcLine   = ftbit->buffer;
  139. +    unsigned char*   dstLine   = target->buffer;
  140. +    int              src_pitch = ftbit->pitch;
  141. +    int              width     = target->width;
  142. +    int              height    = target->rows;
  143. +    int              pitch     = target->pitch;
  144. +    int              subpixel;
  145. +    int              h;
  146. +
  147. +    subpixel = ( mode == FT_RENDER_MODE_LCD ||
  148. +        mode == FT_RENDER_MODE_LCD_V );
  149. +
  150. +    if ( src_pitch < 0 )
  151. +      srcLine -= src_pitch*(ftbit->rows-1);
  152. +
  153. +    target->pixel_mode = ftbit->pixel_mode;
  154. +
  155. +    switch ( ftbit->pixel_mode )
  156. +    {
  157. +    case FT_PIXEL_MODE_MONO:
  158. +        if ( subpixel )  /* convert mono to ARGB32 values */
  159. +        {
  160. +            for ( h = height; h > 0; h--, srcLine += src_pitch, dstLine += pitch )
  161. +            {
  162. +                int  x;
  163. +
  164. +                for ( x = 0; x < width; x++ )
  165. +                {
  166. +                    if ( srcLine[(x >> 3)] & (0x80 >> (x & 7)) )
  167. +                        ((unsigned int*)dstLine)[x] = 0xffffffffU;
  168. +                }
  169. +            }
  170. +            target->pixel_mode = FT_PIXEL_MODE_LCD;
  171. +        }
  172. +        else if ( mode == FT_RENDER_MODE_NORMAL )  /* convert mono to 8-bit gray */
  173. +        {
  174. +            for ( h = height; h > 0; h--, srcLine += src_pitch, dstLine += pitch )
  175. +            {
  176. +                int  x;
  177. +
  178. +                for ( x = 0; x < width; x++ )
  179. +                {
  180. +                    if ( srcLine[(x >> 3)] & (0x80 >> (x & 7)) )
  181. +                        dstLine[x] = 0xff;
  182. +                }
  183. +            }
  184. +            target->pixel_mode = FT_PIXEL_MODE_GRAY;
  185. +        }
  186. +        else  /* copy mono to mono */
  187. +        {
  188. +            int  bytes = (width+7) >> 3;
  189. +
  190. +            for ( h = height; h > 0; h--, srcLine += src_pitch, dstLine += pitch )
  191. +                memcpy( dstLine, srcLine, bytes );
  192. +        }
  193. +        break;
  194. +
  195. +    case FT_PIXEL_MODE_GRAY:
  196. +        if ( subpixel )  /* convert gray to ARGB32 values */
  197. +        {
  198. +            for ( h = height; h > 0; h--, srcLine += src_pitch, dstLine += pitch )
  199. +            {
  200. +                int            x;
  201. +                unsigned int*  dst = (unsigned int*)dstLine;
  202. +
  203. +                for ( x = 0; x < width; x++ )
  204. +                {
  205. +                    unsigned int  pix = srcLine[x];
  206. +
  207. +                    pix |= (pix << 8);
  208. +                    pix |= (pix << 16);
  209. +
  210. +                    dst[x] = pix;
  211. +                }
  212. +            }
  213. +            target->pixel_mode = FT_PIXEL_MODE_LCD;
  214. +        }
  215. +        else  /* copy gray into gray */
  216. +        {
  217. +            for ( h = height; h > 0; h--, srcLine += src_pitch, dstLine += pitch )
  218. +                memcpy( dstLine, srcLine, width );
  219. +        }
  220. +        break;
  221. +
  222. +    case FT_PIXEL_MODE_LCD:
  223. +        if ( !bgr )
  224. +        {
  225. +            /* convert horizontal RGB into ARGB32 */
  226. +            for ( h = height; h > 0; h--, srcLine += src_pitch, dstLine += pitch )
  227. +            {
  228. +                int            x;
  229. +                unsigned char* src = srcLine;
  230. +                unsigned int*  dst = (unsigned int*)dstLine;
  231. +
  232. +                for ( x = 0; x < width; x++, src += 3 )
  233. +                {
  234. +                    unsigned int  pix;
  235. +
  236. +                    pix = ((unsigned int)src[0] << 16) |
  237. +                          ((unsigned int)src[1] <<  8) |
  238. +                          ((unsigned int)src[2]      ) |
  239. +                          ((unsigned int)src[1] << 24) ;
  240. +
  241. +                    dst[x] = pix;
  242. +                }
  243. +            }
  244. +        }
  245. +        else
  246. +        {
  247. +          /* convert horizontal BGR into ARGB32 */
  248. +          for ( h = height; h > 0; h--, srcLine += src_pitch, dstLine += pitch )
  249. +          {
  250. +              int            x;
  251. +              unsigned char* src = srcLine;
  252. +              unsigned int*  dst = (unsigned int*)dstLine;
  253. +
  254. +              for ( x = 0; x < width; x++, src += 3 )
  255. +              {
  256. +                  unsigned int  pix;
  257. +
  258. +                  pix = ((unsigned int)src[2] << 16) |
  259. +                        ((unsigned int)src[1] <<  8) |
  260. +                        ((unsigned int)src[0]      ) |
  261. +                        ((unsigned int)src[1] << 24) ;
  262. +
  263. +                  dst[x] = pix;
  264. +              }
  265. +          }
  266. +        }
  267. +        break;
  268. +
  269. +    default:  /* FT_PIXEL_MODE_LCD_V */
  270. +        /* convert vertical RGB into ARGB32 */
  271. +        if ( !bgr )
  272. +        {
  273. +            for ( h = height; h > 0; h--, srcLine += 3*src_pitch, dstLine += pitch )
  274. +            {
  275. +                int            x;
  276. +                unsigned char* src = srcLine;
  277. +                unsigned int*  dst = (unsigned int*)dstLine;
  278. +
  279. +                for ( x = 0; x < width; x++, src += 1 )
  280. +                {
  281. +                    unsigned int  pix;
  282. +#if 1
  283. +                    pix = ((unsigned int)src[0]           << 16) |
  284. +                          ((unsigned int)src[src_pitch]   <<  8) |
  285. +                          ((unsigned int)src[src_pitch*2]      ) |
  286. +                          0xFF000000 ;
  287. +#else
  288. +                    pix = ((unsigned int)src[0]           << 16) |
  289. +                          ((unsigned int)src[src_pitch]   <<  8) |
  290. +                          ((unsigned int)src[src_pitch*2]      ) |
  291. +                          ((unsigned int)src[src_pitch]   << 24) ;
  292.  #endif
  293. -    {    65538*9/13,65538*3/13,65538*1/13 },
  294. -    /* green */
  295. -    {    65538*1/6, 65538*4/6, 65538*1/6 },
  296. -    /* blue */
  297. -    {    65538*1/13,65538*3/13,65538*9/13 },
  298. -};
  299. +                    dst[x] = pix;
  300. +                }
  301. +            }
  302. +        }
  303. +        else
  304. +        {
  305. +            for ( h = height; h > 0; h--, srcLine += 3*src_pitch, dstLine += pitch )
  306. +            {
  307. +                int            x;
  308. +                unsigned char* src = srcLine;
  309. +                unsigned int*  dst = (unsigned int*)dstLine;
  310. +
  311. +                for ( x = 0; x < width; x++, src += 1 )
  312. +                {
  313. +                    unsigned int  pix;
  314. +
  315. +                    pix = ((unsigned int)src[src_pitch*2] << 16) |
  316. +                        ((unsigned int)src[src_pitch]   <<  8) |
  317. +                        ((unsigned int)src[0]                ) |
  318. +                        ((unsigned int)src[src_pitch]   << 24) ;
  319. +
  320. +                    dst[x] = pix;
  321. +                }
  322. +            }
  323. +        }
  324. +    }
  325. +}
  326. +
  327.  
  328.  /* Fills in val->image with an image surface created from @bitmap
  329.   */
  330.  -736,7 +1015,7 @@ _get_bitmap_surface (FT_Bitmap            *bi
  331.      int width, height, stride;
  332.      unsigned char *data;
  333.      int format = CAIRO_FORMAT_A8;
  334. -    cairo_bool_t subpixel = FALSE;
  335. +    cairo_image_surface_t  *image;
  336.  
  337.      width = bitmap->width;
  338.      height = bitmap->rows;
  339.  -747,7 +1026,9 @@ _get_bitmap_surface (FT_Bitmap            *bi
  340.     return (*surface)->base.status;
  341.      }
  342.  
  343. -    switch (bitmap->pixel_mode) {
  344. +    {
  345. +   switch (bitmap->pixel_mode)
  346. +   {
  347.      case FT_PIXEL_MODE_MONO:
  348.     stride = (((width + 31) & ~31) >> 3);
  349.     if (own_buffer) {
  350.  -775,7 +1056,6 @@ _get_bitmap_surface (FT_Bitmap            *bi
  351.         }
  352.         }
  353.     }
  354. -
  355.  #ifndef WORDS_BIGENDIAN
  356.     {
  357.         unsigned char   *d = data;
  358.  -787,17 +1067,15 @@ _get_bitmap_surface (FT_Bitmap          *bi
  359.         }
  360.     }
  361.  #endif
  362. +
  363.     format = CAIRO_FORMAT_A1;
  364.     break;
  365.  
  366.      case FT_PIXEL_MODE_LCD:
  367.      case FT_PIXEL_MODE_LCD_V:
  368.      case FT_PIXEL_MODE_GRAY:
  369. -   switch (font_options->antialias) {
  370. -   case CAIRO_ANTIALIAS_DEFAULT:
  371. -   case CAIRO_ANTIALIAS_GRAY:
  372. -   case CAIRO_ANTIALIAS_NONE:
  373. -   default:
  374. +            if (font_options->antialias != CAIRO_ANTIALIAS_SUBPIXEL)
  375. +            {
  376.         stride = bitmap->pitch;
  377.         if (own_buffer) {
  378.         data = bitmap->buffer;
  379.  -809,104 +1087,10 @@ _get_bitmap_surface (FT_Bitmap             *bi
  380.         memcpy (data, bitmap->buffer, stride * height);
  381.         }
  382.         format = CAIRO_FORMAT_A8;
  383. -       break;
  384. -   case CAIRO_ANTIALIAS_SUBPIXEL: {
  385. -       int         x, y;
  386. -       unsigned char   *in_line, *out_line, *in;
  387. -       unsigned int    *out;
  388. -       unsigned int    red, green, blue;
  389. -       int         rf, gf, bf;
  390. -       int         s;
  391. -       int         o, os;
  392. -       unsigned char   *data_rgba;
  393. -       unsigned int    width_rgba, stride_rgba;
  394. -       int         vmul = 1;
  395. -       int         hmul = 1;
  396. -
  397. -       switch (font_options->subpixel_order) {
  398. -       case CAIRO_SUBPIXEL_ORDER_DEFAULT:
  399. -       case CAIRO_SUBPIXEL_ORDER_RGB:
  400. -       case CAIRO_SUBPIXEL_ORDER_BGR:
  401. -       default:
  402. -       width /= 3;
  403. -       hmul = 3;
  404. -       break;
  405. -       case CAIRO_SUBPIXEL_ORDER_VRGB:
  406. -       case CAIRO_SUBPIXEL_ORDER_VBGR:
  407. -       vmul = 3;
  408. -       height /= 3;
  409. -       break;
  410. -       }
  411. -       /*
  412. -        * Filter the glyph to soften the color fringes
  413. -        */
  414. -       width_rgba = width;
  415. +       } else {
  416. +       data = bitmap->buffer;
  417.         stride = bitmap->pitch;
  418. -       stride_rgba = (width_rgba * 4 + 3) & ~3;
  419. -       data_rgba = calloc (stride_rgba, height);
  420. -       if (data_rgba == NULL) {
  421. -       if (own_buffer)
  422. -           free (bitmap->buffer);
  423. -       return _cairo_error (CAIRO_STATUS_NO_MEMORY);
  424. -       }
  425. -
  426. -       os = 1;
  427. -       switch (font_options->subpixel_order) {
  428. -       case CAIRO_SUBPIXEL_ORDER_VRGB:
  429. -       os = stride;
  430. -       case CAIRO_SUBPIXEL_ORDER_DEFAULT:
  431. -       case CAIRO_SUBPIXEL_ORDER_RGB:
  432. -       default:
  433. -       rf = 0;
  434. -       gf = 1;
  435. -       bf = 2;
  436. -       break;
  437. -       case CAIRO_SUBPIXEL_ORDER_VBGR:
  438. -       os = stride;
  439. -       case CAIRO_SUBPIXEL_ORDER_BGR:
  440. -       bf = 0;
  441. -       gf = 1;
  442. -       rf = 2;
  443. -       break;
  444. -       }
  445. -       in_line = bitmap->buffer;
  446. -       out_line = data_rgba;
  447. -       for (y = 0; y < height; y++)
  448. -       {
  449. -       in = in_line;
  450. -       out = (unsigned int *) out_line;
  451. -       in_line += stride * vmul;
  452. -       out_line += stride_rgba;
  453. -       for (x = 0; x < width * hmul; x += hmul)
  454. -       {
  455. -           red = green = blue = 0;
  456. -           o = 0;
  457. -           for (s = 0; s < 3; s++)
  458. -           {
  459. -           red += filters[rf][s]*in[x+o];
  460. -           green += filters[gf][s]*in[x+o];
  461. -           blue += filters[bf][s]*in[x+o];
  462. -           o += os;
  463. -           }
  464. -           red = red / 65536;
  465. -           green = green / 65536;
  466. -           blue = blue / 65536;
  467. -           *out++ = (green << 24) | (red << 16) | (green << 8) | blue;
  468. -       }
  469. -       }
  470. -
  471. -       /* Images here are stored in native format. The
  472. -        * backend must convert to its own format as needed
  473. -        */
  474. -
  475. -       if (own_buffer)
  476. -       free (bitmap->buffer);
  477. -       data = data_rgba;
  478. -       stride = stride_rgba;
  479.         format = CAIRO_FORMAT_ARGB32;
  480. -       subpixel = TRUE;
  481. -       break;
  482. -   }
  483.     }
  484.     break;
  485.      case FT_PIXEL_MODE_GRAY2:
  486.  -918,20 +1102,19 @@ _get_bitmap_surface (FT_Bitmap          *bi
  487.     return _cairo_error (CAIRO_STATUS_NO_MEMORY);
  488.      }
  489.  
  490. -    *surface = (cairo_image_surface_t *)
  491. +    *surface = image = (cairo_image_surface_t *)
  492.     cairo_image_surface_create_for_data (data,
  493.                          format,
  494.                          width, height, stride);
  495. -    if ((*surface)->base.status) {
  496. +    if (image->base.status) {
  497.     free (data);
  498.     return _cairo_error (CAIRO_STATUS_NO_MEMORY);
  499.      }
  500.  
  501. -    if (subpixel)
  502. -   pixman_image_set_component_alpha ((*surface)->pixman_image, TRUE);
  503. -
  504. -    _cairo_image_surface_assume_ownership_of_data ((*surface));
  505. -
  506. +    if (font_options->antialias == CAIRO_ANTIALIAS_SUBPIXEL)
  507. +   pixman_image_set_component_alpha (image->pixman_image, TRUE);
  508. +    _cairo_image_surface_assume_ownership_of_data (image);
  509. +    }
  510.      return CAIRO_STATUS_SUCCESS;
  511.  }
  512.  
  513.  -955,16 +1138,44 @@ _render_glyph_outline (FT_Face          
  514.                cairo_font_options_t  *font_options,
  515.                cairo_image_surface_t    **surface)
  516.  {
  517. +    int rgba = FC_RGBA_UNKNOWN;
  518.      FT_GlyphSlot glyphslot = face->glyph;
  519.      FT_Outline *outline = &glyphslot->outline;
  520.      FT_Bitmap bitmap;
  521.      FT_BBox cbox;
  522. -    FT_Matrix matrix;
  523. -    int hmul = 1;
  524. -    int vmul = 1;
  525.      unsigned int width, height, stride;
  526. -    cairo_bool_t subpixel = FALSE;
  527. +    cairo_format_t format;
  528.      cairo_status_t status;
  529. +    FT_Error  fterror;
  530. +    FT_Library  library = glyphslot->library;
  531. +    FT_Render_Mode  render_mode = FT_RENDER_MODE_NORMAL;
  532. +
  533. +    switch (font_options->antialias)
  534. +    {
  535. +    case CAIRO_ANTIALIAS_NONE:
  536. +        render_mode = FT_RENDER_MODE_MONO;
  537. +        break;
  538. +
  539. +    case CAIRO_ANTIALIAS_SUBPIXEL:
  540. +        switch (font_options->subpixel_order)
  541. +        {
  542. +            case CAIRO_SUBPIXEL_ORDER_DEFAULT:
  543. +            case CAIRO_SUBPIXEL_ORDER_RGB:
  544. +            case CAIRO_SUBPIXEL_ORDER_BGR:
  545. +                render_mode = FT_RENDER_MODE_LCD;
  546. +                break;
  547. +
  548. +            case CAIRO_SUBPIXEL_ORDER_VRGB:
  549. +            case CAIRO_SUBPIXEL_ORDER_VBGR:
  550. +                render_mode = FT_RENDER_MODE_LCD_V;
  551. +                break;
  552. +        }
  553. +        break;
  554. +
  555. +    case CAIRO_ANTIALIAS_DEFAULT:
  556. +    case CAIRO_ANTIALIAS_GRAY:
  557. +        render_mode = FT_RENDER_MODE_NORMAL;
  558. +    }
  559.  
  560.      FT_Outline_Get_CBox (outline, &cbox);
  561.  
  562.  -975,20 +1186,18 @@ _render_glyph_outline (FT_Face          
  563.  
  564.      width = (unsigned int) ((cbox.xMax - cbox.xMin) >> 6);
  565.      height = (unsigned int) ((cbox.yMax - cbox.yMin) >> 6);
  566. -    stride = (width * hmul + 3) & ~3;
  567. +    stride = (width + 3) & ~3;
  568.  
  569.      if (width * height == 0) {
  570. -   cairo_format_t format;
  571.     /* Looks like fb handles zero-sized images just fine */
  572. -   switch (font_options->antialias) {
  573. -   case CAIRO_ANTIALIAS_NONE:
  574. +   switch (render_mode) {
  575. +   case FT_RENDER_MODE_MONO:
  576.         format = CAIRO_FORMAT_A1;
  577.         break;
  578. -   case CAIRO_ANTIALIAS_SUBPIXEL:
  579. +   case FT_RENDER_MODE_LCD:
  580. +   case FT_RENDER_MODE_LCD_V:
  581.         format= CAIRO_FORMAT_ARGB32;
  582.         break;
  583. -   case CAIRO_ANTIALIAS_DEFAULT:
  584. -   case CAIRO_ANTIALIAS_GRAY:
  585.     default:
  586.         format = CAIRO_FORMAT_A8;
  587.         break;
  588.  -999,75 +1208,60 @@ _render_glyph_outline (FT_Face          
  589.     if ((*surface)->base.status)
  590.         return (*surface)->base.status;
  591.      } else  {
  592. +   int bitmap_size;
  593.  
  594. -   matrix.xx = matrix.yy = 0x10000L;
  595. -   matrix.xy = matrix.yx = 0;
  596. -
  597. -   switch (font_options->antialias) {
  598. -   case CAIRO_ANTIALIAS_NONE:
  599. -       bitmap.pixel_mode = FT_PIXEL_MODE_MONO;
  600. -       bitmap.num_grays  = 1;
  601. -       stride = ((width + 31) & -32) >> 3;
  602. -       break;
  603. -   case CAIRO_ANTIALIAS_DEFAULT:
  604. -   case CAIRO_ANTIALIAS_GRAY:
  605. -       bitmap.pixel_mode = FT_PIXEL_MODE_GRAY;
  606. -       bitmap.num_grays  = 256;
  607. -       stride = (width + 3) & -4;
  608. +   switch (render_mode) {
  609. +   case FT_RENDER_MODE_LCD:
  610. +       if(font_options->subpixel_order == CAIRO_SUBPIXEL_ORDER_BGR) {
  611. +       rgba = FC_RGBA_BGR;
  612. +       } else {
  613. +       rgba = FC_RGBA_RGB;
  614. +       }
  615.         break;
  616. -   case CAIRO_ANTIALIAS_SUBPIXEL:
  617. -       switch (font_options->subpixel_order) {
  618. -       case CAIRO_SUBPIXEL_ORDER_RGB:
  619. -       case CAIRO_SUBPIXEL_ORDER_BGR:
  620. -       case CAIRO_SUBPIXEL_ORDER_DEFAULT:
  621. -       default:
  622. -       matrix.xx *= 3;
  623. -       hmul = 3;
  624. -       subpixel = TRUE;
  625. -       break;
  626. -       case CAIRO_SUBPIXEL_ORDER_VRGB:
  627. -       case CAIRO_SUBPIXEL_ORDER_VBGR:
  628. -       matrix.yy *= 3;
  629. -       vmul = 3;
  630. -       subpixel = TRUE;
  631. -       break;
  632. +   case FT_RENDER_MODE_LCD_V:
  633. +       if(font_options->subpixel_order == CAIRO_SUBPIXEL_ORDER_BGR) {
  634. +       rgba = FC_RGBA_VBGR;
  635. +       } else {
  636. +       rgba = FC_RGBA_VRGB;
  637.         }
  638. -       FT_Outline_Transform (outline, &matrix);
  639. -
  640. -       bitmap.pixel_mode = FT_PIXEL_MODE_GRAY;
  641. -       bitmap.num_grays  = 256;
  642. -       stride = (width * hmul + 3) & -4;
  643. -   }
  644. -
  645. -   bitmap.pitch = stride;
  646. -   bitmap.width = width * hmul;
  647. -   bitmap.rows = height * vmul;
  648. -   bitmap.buffer = calloc (stride, bitmap.rows);
  649. -   if (bitmap.buffer == NULL) {
  650. -       return _cairo_error (CAIRO_STATUS_NO_MEMORY);
  651. +       break;
  652. +   default:
  653. +       break;
  654.     }
  655.  
  656. -   FT_Outline_Translate (outline, -cbox.xMin*hmul, -cbox.yMin*vmul);
  657. -
  658. -   if (FT_Outline_Get_Bitmap (glyphslot->library, outline, &bitmap) != 0) {
  659. -       free (bitmap.buffer);
  660. +   FT_Library_SetLcdFilter (library, FT_LCD_FILTER_DEFAULT);
  661. +   fterror = FT_Render_Glyph (face->glyph, render_mode);
  662. +   FT_Library_SetLcdFilter (library, FT_LCD_FILTER_NONE);
  663. +   if (fterror != 0) {
  664.         return _cairo_error (CAIRO_STATUS_NO_MEMORY);
  665.     }
  666.  
  667. +   bitmap_size = _compute_xrender_bitmap_size (&bitmap,
  668. +                           face->glyph,
  669. +                           render_mode);
  670. +   if(bitmap_size < 0) {
  671. +       _cairo_error (CAIRO_STATUS_NO_MEMORY);
  672. +       return CAIRO_STATUS_NO_MEMORY;
  673. +   }
  674. +   bitmap.buffer = malloc(bitmap_size);
  675. +   _fill_xrender_bitmap (&bitmap, face->glyph, render_mode,
  676. +                 (rgba == FC_RGBA_BGR || rgba == FC_RGBA_VBGR));
  677.     status = _get_bitmap_surface (&bitmap, TRUE, font_options, surface);
  678.     if (status)
  679.         return status;
  680. -    }
  681.  
  682.      /*
  683.       * Note: the font's coordinate system is upside down from ours, so the
  684.       * Y coordinate of the control box needs to be negated.  Moreover, device
  685.       * offsets are position of glyph origin relative to top left while xMin
  686.       * and yMax are offsets of top left relative to origin.  Another negation.
  687. +     * XXX: No, wait. In 1.5.2 it seems to be the other way around: x negated,
  688. +     * XXX: y literal. What the fuck?..
  689.       */
  690.      cairo_surface_set_device_offset (&(*surface)->base,
  691. -                    floor (-(double) cbox.xMin / 64.0),
  692. -                    floor (+(double) cbox.yMax / 64.0));
  693. +                        (double)-glyphslot->bitmap_left,
  694. +                    (double)glyphslot->bitmap_top);
  695. +    }
  696.  
  697.      return CAIRO_STATUS_SUCCESS;
  698.  }
  699.  -1440,11 +1634,11 @@ _cairo_ft_options_merge (cairo_ft_option
  700.         case CAIRO_SUBPIXEL_ORDER_DEFAULT:
  701.         case CAIRO_SUBPIXEL_ORDER_RGB:
  702.         case CAIRO_SUBPIXEL_ORDER_BGR:
  703. -           load_target |= FT_LOAD_TARGET_LCD;
  704. +           load_target = FT_LOAD_TARGET_LCD;
  705.             break;
  706.         case CAIRO_SUBPIXEL_ORDER_VRGB:
  707.         case CAIRO_SUBPIXEL_ORDER_VBGR:
  708. -           load_target |= FT_LOAD_TARGET_LCD_V;
  709. +           load_target = FT_LOAD_TARGET_LCD_V;
  710.         break;
  711.         }
  712.         }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement