Commit 3528e709 authored by Kenichi Handa's avatar Kenichi Handa

(xftfont_list): Adjusted for the change of `list'

callback function.
(xftfont_match): Adjusted for the fontmat change of font-entity.
(xftfont_open): Adjusted for the format change of font-entity and
font-object.  Adjusted for the change of struct font.  Return a
font-object.  Don't update dpyinfo->smallest_font_height and
dpyinfo->smallest_char_width.
(xftfont_close): Block input while calling XftFontClose.
(xftfont_prepare_face): Don't block input while calling
xftfont_get_colors.  Adjusted for the change of struct font.
(xftfont_shape): Return value of error case fixed.
parent f0c55750
......@@ -137,7 +137,7 @@ xftfont_get_colors (f, face, gc, xftface_info, fg, bg)
static Lisp_Object xftfont_list P_ ((Lisp_Object, Lisp_Object));
static Lisp_Object xftfont_match P_ ((Lisp_Object, Lisp_Object));
static struct font *xftfont_open P_ ((FRAME_PTR, Lisp_Object, int));
static Lisp_Object xftfont_open P_ ((FRAME_PTR, Lisp_Object, int));
static void xftfont_close P_ ((FRAME_PTR, struct font *));
static int xftfont_prepare_face P_ ((FRAME_PTR, struct face *));
static void xftfont_done_face P_ ((FRAME_PTR, struct face *));
......@@ -157,13 +157,12 @@ xftfont_list (frame, spec)
Lisp_Object frame;
Lisp_Object spec;
{
Lisp_Object val = ftfont_driver.list (frame, spec);
Lisp_Object list = ftfont_driver.list (frame, spec), tail;
int i;
if (! NILP (val))
for (i = 0; i < ASIZE (val); i++)
ASET (AREF (val, i), FONT_TYPE_INDEX, Qxft);
return val;
for (tail = list; CONSP (tail); tail = XCDR (tail))
ASET (XCAR (tail), FONT_TYPE_INDEX, Qxft);
return list;
}
static Lisp_Object
......@@ -173,7 +172,7 @@ xftfont_match (frame, spec)
{
Lisp_Object entity = ftfont_driver.match (frame, spec);
if (VECTORP (entity))
if (! NILP (entity))
ASET (entity, FONT_TYPE_INDEX, Qxft);
return entity;
}
......@@ -182,7 +181,7 @@ extern Lisp_Object ftfont_font_format P_ ((FcPattern *));
static FcChar8 ascii_printable[95];
static struct font *
static Lisp_Object
xftfont_open (f, entity, pixel_size)
FRAME_PTR f;
Lisp_Object entity;
......@@ -190,7 +189,7 @@ xftfont_open (f, entity, pixel_size)
{
Display_Info *dpyinfo = FRAME_X_DISPLAY_INFO (f);
Display *display = FRAME_X_DISPLAY (f);
Lisp_Object val;
Lisp_Object val, font_object;
FcPattern *pattern, *pat = NULL;
FcChar8 *file;
struct xftfont_info *xftfont_info = NULL;
......@@ -199,18 +198,19 @@ xftfont_open (f, entity, pixel_size)
double size = 0;
XftFont *xftfont = NULL;
int spacing;
char *name;
int len;
char name[256];
int len, i;
XGlyphInfo extents;
FT_Face ft_face;
val = AREF (entity, FONT_EXTRA_INDEX);
if (XTYPE (val) != Lisp_Misc
|| XMISCTYPE (val) != Lisp_Misc_Save_Value)
return NULL;
pattern = XSAVE_VALUE (val)->pointer;
val = assq_no_quit (QCfont_entity, AREF (entity, FONT_EXTRA_INDEX));
if (! CONSP (val)
|| XTYPE (XCDR (val)) != Lisp_Misc
|| XMISCTYPE (XCDR (val)) != Lisp_Misc_Save_Value)
return Qnil;
pattern = XSAVE_VALUE (XCDR (val))->pointer;
if (FcPatternGetString (pattern, FC_FILE, 0, &file) != FcResultMatch)
return NULL;
return Qnil;
size = XINT (AREF (entity, FONT_SIZE_INDEX));
if (size == 0)
......@@ -228,49 +228,39 @@ xftfont_open (f, entity, pixel_size)
BLOCK_INPUT;
XftDefaultSubstitute (display, FRAME_X_SCREEN_NUMBER (f), pat);
xftfont = XftFontOpenPattern (display, pat);
UNBLOCK_INPUT;
if (! xftfont)
return Qnil;
/* We should not destroy PAT here because it is kept in XFTFONT and
destroyed automatically when XFTFONT is closed. */
if (! xftfont)
goto err;
xftfont_info = malloc (sizeof (struct xftfont_info));
if (! xftfont_info)
goto err;
xfont = malloc (sizeof (XFontStruct));
if (! xfont)
goto err;
font_object = font_make_object (VECSIZE (struct xftfont_info));
ASET (font_object, FONT_TYPE_INDEX, Qxft);
for (i = 1; i < FONT_ENTITY_MAX; i++)
ASET (font_object, i, AREF (entity, i));
ASET (font_object, FONT_SIZE_INDEX, make_number (size));
len = font_unparse_xlfd (entity, size, name, 256);
if (len > 0)
ASET (font_object, FONT_NAME_INDEX, make_unibyte_string (name, len));
len = font_unparse_fcname (entity, size, name, 256);
if (len > 0)
ASET (font_object, FONT_FULLNAME_INDEX, make_unibyte_string (name, len));
else
ASET (font_object, FONT_FULLNAME_INDEX,
AREF (font_object, FONT_NAME_INDEX));
ASET (font_object, FONT_FILE_INDEX,
make_unibyte_string ((char *) file, strlen ((char *) file)));
ASET (font_object, FONT_FORMAT_INDEX, ftfont_font_format (pattern));
font = XFONT_OBJECT (font_object);
font->pixel_size = pixel_size;
font->driver = &xftfont_driver;
font->encoding_charset = font->repertory_charset = -1;
xftfont_info = (struct xftfont_info *) font;
xftfont_info->display = display;
xftfont_info->screen = FRAME_X_SCREEN_NUMBER (f);
xftfont_info->xftfont = xftfont;
#ifdef HAVE_LIBOTF
ft_face = XftLockFace (xftfont);
xftfont_info->maybe_otf = ft_face->face_flags & FT_FACE_FLAG_SFNT;
XftUnlockFace (xftfont);
xftfont_info->otf = NULL;
#endif /* HAVE_LIBOTF */
font = (struct font *) xftfont_info;
font->format = ftfont_font_format (xftfont->pattern);
font->entity = entity;
font->pixel_size = size;
font->driver = &xftfont_driver;
len = 96;
name = malloc (len);
while (name && font_unparse_fcname (entity, pixel_size, name, len) < 0)
{
char *new = realloc (name, len += 32);
if (! new)
free (name);
name = new;
}
if (! name)
goto err;
font->font.full_name = font->font.name = name;
font->file_name = (char *) file;
font->font.size = xftfont->max_advance_width;
font->font.charset = font->encoding_charset = font->repertory_charset = -1;
if (FcPatternGetInteger (xftfont->pattern, FC_SPACING, 0, &spacing)
!= FcResultMatch)
spacing = FC_PROPORTIONAL;
......@@ -280,21 +270,22 @@ xftfont_open (f, entity, pixel_size)
for (i = 0; i < 95; i++)
ascii_printable[i] = ' ' + i;
}
BLOCK_INPUT;
if (spacing != FC_PROPORTIONAL)
{
font->font.average_width = font->font.space_width
font->min_width = font->average_width = font->space_width
= xftfont->max_advance_width;
XftTextExtents8 (display, xftfont, ascii_printable + 1, 94, &extents);
}
else
{
XftTextExtents8 (display, xftfont, ascii_printable, 1, &extents);
font->font.space_width = extents.xOff;
if (font->font.space_width <= 0)
font->space_width = extents.xOff;
if (font->space_width <= 0)
/* dirty workaround */
font->font.space_width = pixel_size;
font->space_width = pixel_size;
XftTextExtents8 (display, xftfont, ascii_printable + 1, 94, &extents);
font->font.average_width = (font->font.space_width + extents.xOff) / 95;
font->average_width = (font->space_width + extents.xOff) / 95;
}
UNBLOCK_INPUT;
......@@ -304,57 +295,37 @@ xftfont_open (f, entity, pixel_size)
font->descent = xftfont->descent;
if (font->descent < extents.height - extents.y)
font->descent = extents.height - extents.y;
font->font.height = font->ascent + font->descent;
font->height = font->ascent + font->descent;
/* Unfortunately Xft doesn't provide a way to get minimum char
width. So, we use space_width instead. */
font->min_width = font->font.space_width;
font->font.baseline_offset = 0;
font->font.relative_compose = 0;
font->font.default_ascent = 0;
font->font.vertical_centering = 0;
/* Setup pseudo XFontStruct */
xfont->fid = 0;
xfont->ascent = font->ascent;
xfont->descent = font->descent;
xfont->max_bounds.descent = font->descent;
xfont->max_bounds.width = xftfont->max_advance_width;
xfont->min_bounds.width = font->font.space_width;
font->font.font = xfont;
dpyinfo->n_fonts++;
/* Set global flag fonts_changed_p to non-zero if the font loaded
has a character with a smaller width than any other character
before, or if the font loaded has a smaller height than any other
font loaded before. If this happens, it will make a glyph matrix
reallocation necessary. */
if (dpyinfo->n_fonts == 1)
ft_face = XftLockFace (xftfont);
if (XINT (AREF (entity, FONT_SIZE_INDEX)) == 0)
{
dpyinfo->smallest_font_height = font->font.height;
dpyinfo->smallest_char_width = font->min_width;
fonts_changed_p = 1;
int upEM = ft_face->units_per_EM;
font->underline_position = -ft_face->underline_position * size / upEM;
font->underline_thickness = -ft_face->underline_thickness * size / upEM;
}
else
{
if (dpyinfo->smallest_font_height > font->font.height)
dpyinfo->smallest_font_height = font->font.height,
fonts_changed_p |= 1;
if (dpyinfo->smallest_char_width > font->min_width)
dpyinfo->smallest_char_width = font->min_width,
fonts_changed_p |= 1;
font->underline_position = -1;
font->underline_thickness = 0;
}
#ifdef HAVE_LIBOTF
xftfont_info->maybe_otf = ft_face->face_flags & FT_FACE_FLAG_SFNT;
xftfont_info->otf = NULL;
#endif /* HAVE_LIBOTF */
XftUnlockFace (xftfont);
return font;
/* Unfortunately Xft doesn't provide a way to get minimum char
width. So, we use space_width instead. */
font->min_width = font->space_width;
err:
if (xftfont) XftFontClose (display, xftfont);
UNBLOCK_INPUT;
if (xftfont_info) free (xftfont_info);
if (xfont) free (xfont);
return NULL;
font->baseline_offset = 0;
font->relative_compose = 0;
font->default_ascent = 0;
font->vertical_centering = 0;
return font_object;
}
static void
......@@ -368,11 +339,9 @@ xftfont_close (f, font)
if (xftfont_info->otf)
OTF_close (xftfont_info->otf);
#endif
BLOCK_INPUT;
XftFontClose (xftfont_info->display, xftfont_info->xftfont);
if (font->font.name)
free (font->font.name);
free (font);
FRAME_X_DISPLAY_INFO (f)->n_fonts--;
UNBLOCK_INPUT;
}
static int
......@@ -394,12 +363,8 @@ xftfont_prepare_face (f, face)
xftface_info = malloc (sizeof (struct xftface_info));
if (! xftface_info)
return -1;
BLOCK_INPUT;
xftfont_get_colors (f, face, face->gc, NULL,
&xftface_info->xft_fg, &xftface_info->xft_bg);
UNBLOCK_INPUT;
face->extra = xftface_info;
return 0;
}
......@@ -491,7 +456,7 @@ xftfont_draw (s, from, to, x, y, with_background)
{
FRAME_PTR f = s->f;
struct face *face = s->face;
struct xftfont_info *xftfont_info = (struct xftfont_info *) s->font_info;
struct xftfont_info *xftfont_info = (struct xftfont_info *) s->font;
struct xftface_info *xftface_info = NULL;
XftDraw *xft_draw = xftfont_get_xft_draw (f);
FT_UInt *code;
......@@ -500,7 +465,7 @@ xftfont_draw (s, from, to, x, y, with_background)
int len = to - from;
int i;
if (s->font_info == face->font_info)
if (s->font == face->font)
xftface_info = (struct xftface_info *) face->extra;
xftfont_get_colors (f, face, s->gc, xftface_info,
&fg, with_background ? &bg : NULL);
......@@ -511,12 +476,8 @@ xftfont_draw (s, from, to, x, y, with_background)
XftDrawSetClip (xft_draw, NULL);
if (with_background)
{
struct font *font = (struct font *) face->font_info;
XftDrawRect (xft_draw, &bg,
x, y - face->font->ascent, s->width, font->font.height);
}
XftDrawRect (xft_draw, &bg,
x, y - face->font->ascent, s->width, face->font->height);
code = alloca (sizeof (FT_UInt) * len);
for (i = 0; i < len; i++)
code[i] = ((XCHAR2B_BYTE1 (s->char2b + from + i) << 8)
......@@ -584,7 +545,7 @@ xftfont_shape (lgstring)
{
struct font *font;
struct xftfont_info *xftfont_info;
int result;
Lisp_Object result;
FT_Face ft_face;
CHECK_FONT_GET_OBJECT (LGSTRING_FONT (lgstring), font);
......@@ -602,7 +563,7 @@ xftfont_shape (lgstring)
OTF_close (otf);
xftfont_info->maybe_otf = 0;
XftUnlockFace (xftfont_info->xftfont);
return 0;
return Qnil;
}
xftfont_info->otf = otf;
}
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment