From d52d59bc32a9e5bb3f7dfc0a88a02715555b9870 Mon Sep 17 00:00:00 2001 From: Bakkeby Date: Mon, 21 Mar 2022 22:25:51 +0100 Subject: [PATCH] drw_text: print whole utf-8 characters only and simplify ellipsis handling --- drw.c | 50 +++++++++++++++++++++++++------------------------- 1 file changed, 25 insertions(+), 25 deletions(-) diff --git a/drw.c b/drw.c index 4cdbcbe..ccb3b9a 100644 --- a/drw.c +++ b/drw.c @@ -251,12 +251,10 @@ drw_rect(Drw *drw, int x, int y, unsigned int w, unsigned int h, int filled, int int drw_text(Drw *drw, int x, int y, unsigned int w, unsigned int h, unsigned int lpad, const char *text, int invert) { - char buf[1024]; int ty; unsigned int ew; XftDraw *d = NULL; Fnt *usedfont, *curfont, *nextfont; - size_t i, len; int utf8strlen, utf8charlen, render = x || y || w || h; long utf8codepoint = 0; const char *utf8str; @@ -264,7 +262,9 @@ drw_text(Drw *drw, int x, int y, unsigned int w, unsigned int h, unsigned int lp FcPattern *fcpattern; FcPattern *match; XftResult result; - int charexists = 0; + int charexists = 0, overflow = 0; + XGlyphInfo ext; + const char *ellipsis = "..."; if (!drw || (render && !drw->scheme) || !text || !drw->fonts) return 0; @@ -278,7 +278,7 @@ drw_text(Drw *drw, int x, int y, unsigned int w, unsigned int h, unsigned int lp DefaultVisual(drw->dpy, drw->screen), DefaultColormap(drw->dpy, drw->screen)); x += lpad; - w -= lpad; + w -= lpad * 2; } usedfont = drw->fonts; @@ -286,12 +286,19 @@ drw_text(Drw *drw, int x, int y, unsigned int w, unsigned int h, unsigned int lp utf8strlen = 0; utf8str = text; nextfont = NULL; + ew = 0; while (*text) { utf8charlen = utf8decode(text, &utf8codepoint, UTF_SIZ); for (curfont = drw->fonts; curfont; curfont = curfont->next) { charexists = charexists || XftCharExists(drw->dpy, curfont->xfont, utf8codepoint); if (charexists) { if (curfont == usedfont) { + XftTextExtentsUtf8(usedfont->dpy, usedfont->xfont, (XftChar8 *)text, utf8charlen, &ext); + if (ew + ext.xOff > w) { + overflow = 1; + break; + } + ew += ext.xOff; utf8strlen += utf8charlen; text += utf8charlen; } else { @@ -301,36 +308,29 @@ drw_text(Drw *drw, int x, int y, unsigned int w, unsigned int h, unsigned int lp } } - if (!charexists || nextfont) + if (overflow || !charexists || nextfont) break; else charexists = 0; } if (utf8strlen) { - drw_font_getexts(usedfont, utf8str, utf8strlen, &ew, NULL); - /* shorten text if necessary */ - for (len = MIN(utf8strlen, sizeof(buf) - 1); len && ew > w; len--) - drw_font_getexts(usedfont, utf8str, len, &ew, NULL); - - if (len) { - memcpy(buf, utf8str, len); - buf[len] = '\0'; - if (len < utf8strlen) - for (i = len; i && i > len - 3; buf[--i] = '.') - ; /* NOP */ - - if (render) { - ty = y + (h - usedfont->h) / 2 + usedfont->xfont->ascent; - XftDrawStringUtf8(d, &drw->scheme[invert ? ColBg : ColFg], - usedfont->xfont, x, ty, (XftChar8 *)buf, len); - } - x += ew; - w -= ew; + if (render) { + ty = y + (h - usedfont->h) / 2 + usedfont->xfont->ascent; + XftDrawStringUtf8(d, &drw->scheme[invert ? ColBg : ColFg], + usedfont->xfont, x, ty, (XftChar8 *)utf8str, utf8strlen); + } + x += ew; + w -= ew; + if (render && overflow) { + XftTextExtentsUtf8(drw->fonts->dpy, drw->fonts->xfont, (XftChar8 *)ellipsis, 3, &ext); + XFillRectangle(drw->dpy, drw->drawable, drw->gc, x + w - ext.xOff, y, ext.xOff, h); + XftDrawStringUtf8(d, &drw->scheme[invert ? ColBg : ColFg], + usedfont->xfont, x + w - ext.xOff, ty, (XftChar8 *)ellipsis, 3); } } - if (!*text) { + if (overflow || !*text) { break; } else if (nextfont) { charexists = 0; -- 2.25.1