From: handa Date: Wed, 17 Mar 2004 12:56:57 +0000 (+0000) Subject: *** empty log message *** X-Git-Url: http://git.chise.org/gitweb/?a=commitdiff_plain;h=92c907e4916b77f1725cb4660cc0ce077e526f56;p=m17n%2Fm17n-lib.git *** empty log message *** --- diff --git a/src/face.c b/src/face.c index 216eafa..14d5cd0 100644 --- a/src/face.c +++ b/src/face.c @@ -386,6 +386,8 @@ deserialize_face (MPlist *plist) return face; } +static MGlyphString work_gstring; + /* Internal API */ @@ -515,6 +517,11 @@ mface__init () mface_yellow->property[MFACE_FOREGROUND] = (void *) msymbol ("yellow"); mface_magenta = mface (); mface_magenta->property[MFACE_FOREGROUND] = (void *) msymbol ("magenta"); + + work_gstring.glyphs = malloc (sizeof (MGlyph) * 2); + work_gstring.size = 2; + work_gstring.used = 0; + work_gstring.inc = 1; return 0; } @@ -608,12 +615,14 @@ mface__realize (MFrame *frame, MFace **faces, int num, { rface->rfont = rfont; g.otf_encoded = 0; - mfont__get_metric (rfont, &g); - rface->space_width = g.width; - g.code = MCHAR_INVALID_CODE; - mfont__get_metric (rface->rfont, &g); - rface->ascent = g.ascent; - rface->descent = g.descent; + work_gstring.glyphs[0] = g; + work_gstring.glyphs[0].rface = rface; + work_gstring.glyphs[1].code = MCHAR_INVALID_CODE; + work_gstring.glyphs[1].rface = rface; + mfont__get_metric (&work_gstring, 0, 2); + rface->space_width = work_gstring.glyphs[0].width; + rface->ascent = work_gstring.glyphs[1].ascent; + rface->descent = work_gstring.glyphs[1].descent; } else { @@ -664,12 +673,11 @@ mface__for_chars (MSymbol script, MSymbol language, MSymbol charset, *rface = *from_g->rface->ascii_rface; rface->rfont = rfont; { - MGlyph tmp; - - tmp.code = MCHAR_INVALID_CODE; - mfont__get_metric (rfont, &tmp); - rface->ascent = tmp.ascent; - rface->descent = tmp.descent; + work_gstring.glyphs[0].code = MCHAR_INVALID_CODE; + work_gstring.glyphs[0].rface = rface; + mfont__get_metric (&work_gstring, 0, 1); + rface->ascent = work_gstring.glyphs[0].ascent; + rface->descent = work_gstring.glyphs[0].descent; } mwin__realize_face (rface); mplist_add (from_g->rface->frame->realized_face_list, Mt, rface); diff --git a/src/font-ft.c b/src/font-ft.c index 0733afe..e93fb04 100644 --- a/src/font-ft.c +++ b/src/font-ft.c @@ -261,7 +261,7 @@ build_font_list () static MRealizedFont *ft_select (MFrame *, MFont *, MFont *, int); static int ft_open (MRealizedFont *); static void ft_close (MRealizedFont *); -static void ft_find_metric (MRealizedFont *, MGlyph *); +static void ft_find_metric (MRealizedFont *, MGlyphString *, int, int); static unsigned ft_encode_char (MRealizedFont *, int, unsigned); static void ft_render (MDrawWindow, int, int, MGlyphString *, MGlyph *, MGlyph *, int, MDrawRegion); @@ -400,39 +400,54 @@ ft_close (MRealizedFont *rfont) /* The FreeType font driver function FIND_METRIC. */ static void -ft_find_metric (MRealizedFont *rfont, MGlyph *g) +ft_find_metric (MRealizedFont *rfont, MGlyphString *gstring, + int from, int to) { MFTInfo *ft_info = (MFTInfo *) rfont->info; FT_Face ft_face = ft_info->ft_face; + MGlyph *g = MGLYPH (from), *gend = MGLYPH (to); + FT_Int32 load_flags = FT_LOAD_RENDER; - if (g->code == MCHAR_INVALID_CODE) + if (! gstring->anti_alias) { - unsigned unitsPerEm = ft_face->units_per_EM; - int size = rfont->font.property[MFONT_SIZE] / 10; - - g->lbearing = 0; - g->rbearing = ft_face->max_advance_width * size / unitsPerEm; - g->width = ft_face->max_advance_width * size / unitsPerEm; - g->ascent = ft_face->ascender * size / unitsPerEm; - g->descent = (- ft_face->descender) * size / unitsPerEm; +#ifdef FT_LOAD_TARGET_MONO + load_flags |= FT_LOAD_TARGET_MONO; +#else + load_flags |= FT_LOAD_MONOCHROME; +#endif } - else - { - FT_Glyph_Metrics *metrics; - FT_UInt code; - if (g->otf_encoded) - code = g->code; + for (; g != gend; g++) + { + if (g->code == MCHAR_INVALID_CODE) + { + unsigned unitsPerEm = ft_face->units_per_EM; + int size = rfont->font.property[MFONT_SIZE] / 10; + + g->lbearing = 0; + g->rbearing = ft_face->max_advance_width * size / unitsPerEm; + g->width = ft_face->max_advance_width * size / unitsPerEm; + g->ascent = ft_face->ascender * size / unitsPerEm; + g->descent = (- ft_face->descender) * size / unitsPerEm; + } else - code = FT_Get_Char_Index (ft_face, (FT_ULong) g->code); - - FT_Load_Glyph (ft_face, code, FT_LOAD_RENDER); - metrics = &ft_face->glyph->metrics; - g->lbearing = (metrics->horiBearingX >> 6); - g->rbearing = (metrics->horiBearingX + metrics->width) >> 6; - g->width = metrics->horiAdvance >> 6; - g->ascent = metrics->horiBearingY >> 6; - g->descent = (metrics->height - metrics->horiBearingY) >> 6; + { + FT_Glyph_Metrics *metrics; + FT_UInt code; + + if (g->otf_encoded) + code = g->code; + else + code = FT_Get_Char_Index (ft_face, (FT_ULong) g->code); + + FT_Load_Glyph (ft_face, code, FT_LOAD_RENDER); + metrics = &ft_face->glyph->metrics; + g->lbearing = (metrics->horiBearingX >> 6); + g->rbearing = (metrics->horiBearingX + metrics->width) >> 6; + g->width = metrics->horiAdvance >> 6; + g->ascent = metrics->horiBearingY >> 6; + g->descent = (metrics->height - metrics->horiBearingY) >> 6; + } } } @@ -464,28 +479,31 @@ ft_encode_char (MRealizedFont *rfont, int c, unsigned ignored) /* The FreeType font driver function RENDER. */ -struct { - int size, inc, used; - MDrawPoint *points; -} point_table[8]; +#define NUM_POINTS 0x1000 + +typedef struct { + MDrawPoint points[NUM_POINTS]; + MDrawPoint *p; +} MPointTable; static void ft_render (MDrawWindow win, int x, int y, MGlyphString *gstring, MGlyph *from, MGlyph *to, int reverse, MDrawRegion region) { - MRealizedFace *rface; - MFrame *frame; + MRealizedFace *rface = from->rface; + MFrame *frame = rface->frame; MFTInfo *ft_info; FT_Face ft_face = NULL; FT_Int32 load_flags = FT_LOAD_RENDER; MGlyph *g; int i, j; + MPointTable point_table[8]; if (from == to) return; - if (! gstring->control.anti_alias) + if (! gstring->anti_alias) { #ifdef FT_LOAD_TARGET_MONO load_flags |= FT_LOAD_TARGET_MONO; @@ -496,74 +514,91 @@ ft_render (MDrawWindow win, int x, int y, /* It is assured that the all glyphs in the current range use the same realized face. */ - rface = from->rface; - frame = rface->frame; ft_info = (MFTInfo *) rface->rfont->info; ft_face = ft_info->ft_face; for (i = 0; i < 8; i++) - MLIST_RESET (point_table + i); + point_table[i].p = point_table[i].points; for (g = from; g < to; x += g++->width) { FT_UInt code; unsigned char *bmp; - MDrawPoint p; int intensity; + MPointTable *ptable; + int xoff, yoff; if (g->otf_encoded) code = g->code; else code = FT_Get_Char_Index (ft_face, (FT_ULong) g->code); FT_Load_Glyph (ft_face, code, load_flags); + yoff = y - ft_face->glyph->bitmap_top + g->yoff; bmp = ft_face->glyph->bitmap.buffer; - if (gstring->control.anti_alias) - { - for (i = 0; i < ft_face->glyph->bitmap.rows; - i++, bmp += ft_face->glyph->bitmap.pitch) - for (j = 0; j < ft_face->glyph->bitmap.width; j++) + if (gstring->anti_alias) + for (i = 0; i < ft_face->glyph->bitmap.rows; + i++, bmp += ft_face->glyph->bitmap.pitch, yoff++) + { + xoff = x + ft_face->glyph->bitmap_left + g->xoff; + for (j = 0; j < ft_face->glyph->bitmap.width; j++, xoff++) { intensity = bmp[j] >> 5; if (intensity) { - p.x = x + ft_face->glyph->bitmap_left + g->xoff + j; - p.y = y - ft_face->glyph->bitmap_top + g->yoff + i; - MLIST_APPEND1 (point_table + intensity, points, p, - MERROR_FONT_FT); + ptable = point_table + intensity; + ptable->p->x = xoff; + ptable->p->y = yoff; + ptable->p++; + if (ptable->p - ptable->points == NUM_POINTS) + { + mwin__draw_points (frame, win, rface, + reverse ? 7 - intensity : intensity, + ptable->points, NUM_POINTS, region); + ptable->p = ptable->points; + } } } - } + } else - { - for (i = 0; i < ft_face->glyph->bitmap.rows; - i++, bmp += ft_face->glyph->bitmap.pitch) - for (j = 0; j < ft_face->glyph->bitmap.width; j++) + for (i = 0; i < ft_face->glyph->bitmap.rows; + i++, bmp += ft_face->glyph->bitmap.pitch, yoff++) + { + xoff = x + ft_face->glyph->bitmap_left + g->xoff; + for (j = 0; j < ft_face->glyph->bitmap.width; j++, xoff++) { intensity = bmp[j / 8] & (1 << (7 - (j % 8))); if (intensity) { - p.x = x + ft_face->glyph->bitmap_left + g->xoff + j; - p.y = y - ft_face->glyph->bitmap_top + g->yoff + i; - MLIST_APPEND1 (point_table, points, p, - MERROR_FONT_FT); + ptable = point_table; + ptable->p->x = xoff; + ptable->p->y = yoff; + ptable->p++; + if (ptable->p - ptable->points == NUM_POINTS) + { + mwin__draw_points (frame, win, rface, + reverse ? 0 : 7, + ptable->points, NUM_POINTS, region); + ptable->p = ptable->points; + } } } } } - if (gstring->control.anti_alias) + if (gstring->anti_alias) { for (i = 1; i < 8; i++) - if (point_table[i].used) + if (point_table[i].p != point_table[i].points) mwin__draw_points (frame, win, rface, reverse ? 7 - i : i, - point_table[i].points, point_table[i].used, - gstring->control.anti_alias); + point_table[i].points, + point_table[i].p - point_table[i].points, region); } else { - mwin__draw_points (frame, win, rface, reverse ? 7 : 0, - point_table[0].points, point_table[0].used, - gstring->control.anti_alias); + if (point_table[0].p != point_table[0].points) + mwin__draw_points (frame, win, rface, reverse ? 0 : 7, + point_table[0].points, + point_table[0].p - point_table[0].points, region); } } @@ -603,9 +638,6 @@ mfont__ft_init () mfont__driver_list[MFONT_TYPE_FT] = &ft_driver; - for (i = 0; i < 8; i++) - MLIST_INIT1 (point_table + i, points, 0x1000); - return 0; } diff --git a/src/font.c b/src/font.c index 645f8e8..2cc4f55 100644 --- a/src/font.c +++ b/src/font.c @@ -957,9 +957,22 @@ mfont__encode_char (MRealizedFont *rfont, int c) } void -mfont__get_metric (MRealizedFont *rfont, MGlyph *g) +mfont__get_metric (MGlyphString *gstring, int from, int to) { - (rfont->driver->find_metric) (rfont, g); + MGlyph *from_g = MGLYPH (from), *to_g = MGLYPH (to), *g; + MRealizedFont *rfont = from_g->rface->rfont; + + for (g = from_g; g != to_g; g++) + if (g->rface->rfont != rfont) + { + int idx = GLYPH_INDEX (g); + + (rfont->driver->find_metric) (rfont, gstring, from, idx); + from_g = g; + rfont = g->rface->rfont; + from = idx; + } + (rfont->driver->find_metric) (rfont, gstring, from, GLYPH_INDEX (g)); } diff --git a/src/font.h b/src/font.h index 6c77228..2053328 100644 --- a/src/font.h +++ b/src/font.h @@ -169,7 +169,9 @@ struct MFontDriver /** Close a font specified by RFONT. */ void (*close) (MRealizedFont *rfont); - void (*find_metric) (MRealizedFont *rfont, MGlyph *g); + /** Set metrics of glyphs in GSTRING from FROM to TO. */ + void (*find_metric) (MRealizedFont *rfont, MGlyphString *gstring, + int from, int to); /** Encode C into the glyph code the font. CODE is a code point of C in rfont->encoder->encoding_charset. If the font has no glyph @@ -233,7 +235,7 @@ extern int mfont__open (MRealizedFont *rfont); extern void mfont__close (MRealizedFont *rfont); -extern void mfont__get_metric (MRealizedFont *rfont, MGlyph *g); +extern void mfont__get_metric (MGlyphString *gstring, int from, int to); extern void mfont__set_property (MFont *font, enum MFontProperty key, MSymbol val); diff --git a/src/internal-gui.h b/src/internal-gui.h index bda0e20..656bfb6 100644 --- a/src/internal-gui.h +++ b/src/internal-gui.h @@ -115,6 +115,10 @@ struct MGlyphString /* Members to keep temporary data while layouting. */ short sub_width, sub_lbearing, sub_rbearing; + /* Copied for .anti_alias but never set if the frame's + depth is less than 8. */ + unsigned anti_alias : 1; + MDrawControl control; MDrawRegion region; @@ -239,14 +243,7 @@ extern void mwin__draw_box (MFrame *frame, MDrawWindow win, extern void mwin__draw_points (MFrame *frame, MDrawWindow win, MRealizedFace *rface, int intensity, MDrawPoint *points, int num, - int pixmap); - -extern void mwin__draw_bitmap (MFrame *frame, MDrawWindow win, - MRealizedFace *rface, int reverse, - int x, int y, - int width, int height, int row_bytes, - unsigned char *bmp, - MDrawRegion region, int pixmap); + MDrawRegion region); extern MDrawRegion mwin__region_from_rect (MDrawMetric *rect);