1
/* $XTermId: util.c,v 1.351 2007/03/21 22:04:14 tom Exp $ */
1
/* $XTermId: util.c,v 1.363 2007/06/17 13:52:18 tom Exp $ */
3
3
/* $XFree86: xc/programs/xterm/util.c,v 3.98 2006/06/19 00:36:52 dickey Exp $ */
1442
1442
XClearArea(screen->display, VWindow(screen),
1446
rect_height, False);
1445
(unsigned) rect_width,
1446
(unsigned) rect_height, False);
1448
1448
toprow = y0 / FontHeight(screen);
1449
1449
if (toprow < 0)
1639
* Use this to swap the foreground/background color values in the resource
1640
* data, and to build up a list of the pairs which must be swapped in the
1639
1644
swapLocally(ToSwap * list, int *count, ColorRes * fg, ColorRes * bg)
1650
1655
Pixel bg_color = *bg;
1653
EXCHANGE(*fg, *bg, tmp);
1654
for (n = 0; n < *count; ++n) {
1655
if ((list[n].fg == fg_color && list[n].bg == bg_color)
1656
|| (list[n].fg == bg_color && list[n].bg == fg_color)) {
1662
list[*count].fg = fg_color;
1663
list[*count].bg = bg_color;
1664
*count = *count + 1;
1658
if (fg_color != bg_color) {
1659
EXCHANGE(*fg, *bg, tmp);
1660
for (n = 0; n < *count; ++n) {
1661
if ((list[n].fg == fg_color && list[n].bg == bg_color)
1662
|| (list[n].fg == bg_color && list[n].bg == fg_color)) {
1668
list[*count].fg = fg_color;
1669
list[*count].bg = bg_color;
1670
*count = *count + 1;
1671
TRACE(("swapLocally fg %#lx, bg %#lx ->%d\n", fg_color,
1682
TRACE(("reallySwapColors\n"));
1673
1683
for (j = 0; j < count; ++j) {
1674
1684
for_each_text_gc(k) {
1675
1685
redoCgs(xw, list[j].fg, list[j].bg, (CgsEnum) k);
1709
1719
swapAColor(8, 15);
1722
if (T_COLOR(screen, TEXT_CURSOR) == T_COLOR(screen, TEXT_FG))
1723
T_COLOR(screen, TEXT_CURSOR) = T_COLOR(screen, TEXT_BG);
1712
1725
#define swapTColor(a,b) swapAnyColor(Tcolors, a, b)
1713
1726
swapTColor(TEXT_FG, TEXT_BG);
1714
1727
swapTColor(MOUSE_FG, MOUSE_BG);
1976
#define xtermXftWidth(xw, flags, color, font, x, y, paired_chars, len) \
1977
xtermXftDrawString(xw, flags, color, font, x, y, paired_chars, len, False)
1963
1978
#endif /* OPT_RENDERFONT */
1965
1980
#define DrawX(col) x + (col * (font_width))
1993
2008
case 0x201D: /* groff rq */
2011
case 0x2329: /* groff ".URL" */
2014
case 0x232a: /* groff ".URL" */
1997
2018
if (ch >= 0xff01 && ch <= 0xff5e) {
1998
2019
/* "Fullwidth" codes (actually double-width) */
2185
2209
#define endXftClipping(screen) /* nothing */
2186
2210
#endif /* OPT_CLIP_BOLD */
2214
drawClippedXftString(XtermWidget xw,
2217
XftColor * fg_color,
2220
PAIRED_CHARS(Char * text, Char * text2),
2223
int ncells = xtermXftWidth(xw, flags,
2226
PAIRED_CHARS(text, text2),
2228
TScreen *screen = &(xw->screen);
2230
beginXftClipping(screen, x, y, ncells);
2231
xtermXftDrawString(xw, flags,
2234
PAIRED_CHARS(text, text2),
2237
endXftClipping(screen);
2189
2243
* Draws text with the specified combination of bold/underline. The return
2190
2244
* value is the updated x position.
2203
2257
TScreen *screen = &(xw->screen);
2204
int real_length = len;
2258
Cardinal real_length = len;
2259
Cardinal underline_len = 0;
2206
2260
/* Intended width of the font to draw (as opposed to the actual width of
2207
2261
the X font, and the width of the default font) */
2208
2262
int font_width = ((flags & DOUBLEWFONT) ? 2 : 1) * screen->fnt_wide;
2395
2449
if (!(flags & NOBACKGROUND)) {
2396
2450
XftColor *bg_color = getXftColor(xw, values.background);
2397
ncells = xtermXftDrawString(xw, flags,
2400
PAIRED_CHARS(text, text2),
2451
ncells = xtermXftWidth(xw, flags,
2454
PAIRED_CHARS(text, text2),
2403
2456
XftDrawRect(screen->renderDraw,
2406
ncells * FontWidth(screen),
2459
(unsigned) (ncells * FontWidth(screen)),
2407
2460
(unsigned) FontHeight(screen));
2441
2494
if (xtermIsDecGraphic(ch)) {
2442
2495
/* line drawing character time */
2443
2496
if (last > first) {
2444
ncells = xtermXftDrawString(xw, flags,
2445
getXftColor(xw, values.foreground),
2447
PAIRED_CHARS(text + first,
2451
curX += ncells * FontWidth(screen);
2497
int nc = drawClippedXftString(xw,
2500
getXftColor(xw, values.foreground),
2503
PAIRED_CHARS(text + first,
2505
(Cardinal) (last - first));
2506
curX += nc * FontWidth(screen);
2507
underline_len += nc;
2453
2509
old_wide = screen->fnt_wide;
2454
2510
old_high = screen->fnt_high;
2457
2513
xtermDrawBoxChar(xw, ch, flags, gc,
2458
2514
curX, y - FontAscent(screen));
2459
2515
curX += FontWidth(screen);
2460
2517
screen->fnt_wide = old_wide;
2461
2518
screen->fnt_high = old_high;
2462
2519
first = last + 1;
2465
2522
if (last > first) {
2466
beginXftClipping(screen, curX, y, len);
2467
xtermXftDrawString(xw, flags,
2468
getXftColor(xw, values.foreground),
2470
PAIRED_CHARS(text + first, text2 + first),
2473
endXftClipping(screen);
2524
drawClippedXftString(xw,
2527
getXftColor(xw, values.foreground),
2530
PAIRED_CHARS(text + first,
2532
(Cardinal) (last - first));
2476
2535
#endif /* OPT_BOX_CHARS */
2478
beginXftClipping(screen, x, y, len);
2479
xtermXftDrawString(xw, flags,
2480
getXftColor(xw, values.foreground),
2482
PAIRED_CHARS(text, text2),
2485
endXftClipping(screen);
2538
drawClippedXftString(xw,
2541
getXftColor(xw, values.foreground),
2544
PAIRED_CHARS(text, text2),
2488
2548
if ((flags & UNDERLINE) && screen->underline && !did_ul) {
2491
2551
XDrawLine(screen->display, VWindow(screen), gc,
2493
x + (int) len * FontWidth(screen) - 1,
2553
x + (int) underline_len * FontWidth(screen) - 1,
2496
2556
return x + len * FontWidth(screen);
2539
2599
#if OPT_WIDE_CHARS
2540
2600
if (text2 != 0)
2541
2601
ch |= (text2[last] << 8);
2602
if (ch == HIDDEN_CHAR) {
2604
DrawSegment(first, last);
2542
2608
isMissing = (ch != HIDDEN_CHAR)
2543
2609
&& (xtermMissingChar(xw, ch,
2544
2610
((on_wide || iswide((int) ch))
2749
2815
if (FontDescent(screen) > 1)
2751
2817
XDrawLine(screen->display, VWindow(screen), gc,
2752
x, y, x + underline_len * font_width - 1, y);
2818
x, y, (int) (x + underline_len * font_width - 1), y);
2755
2821
return x + real_length * FontWidth(screen);
2820
2886
#if OPT_HIGHLIGHT_COLOR
2821
2887
Pixel selbg_pix = T_COLOR(screen, HIGHLIGHT_BG);
2822
2888
Pixel selfg_pix = T_COLOR(screen, HIGHLIGHT_FG);
2889
Boolean use_selbg = isNotForeground(xw, fg_pix, bg_pix, selbg_pix);
2890
Boolean use_selfg = isNotBackground(xw, fg_pix, bg_pix, selfg_pix);
2829
2897
checkVeryBoldColors(flags, my_fg);
2831
#if OPT_HIGHLIGHT_COLOR
2833
Bool use_selbg = isNotForeground(xw, fg_pix, bg_pix, selbg_pix);
2834
Bool use_selfg = isNotBackground(xw, fg_pix, bg_pix, selfg_pix);
2899
if (ReverseOrHilite(screen, flags, hilite)) {
2900
if (flags & BOLDATTR(screen)) {
2901
cgsId = gcBoldReverse;
2903
cgsId = gcNormReverse;
2906
EXCHANGE(fg_pix, bg_pix, xx_pix);
2907
#if OPT_HIGHLIGHT_COLOR
2908
if (screen->hilite_reverse) {
2922
if (flags & BOLDATTR(screen)) {
2928
#if OPT_HIGHLIGHT_COLOR
2929
if (hilite && !screen->hilite_reverse) {
2843
if (ReverseOrHilite(screen, flags, hilite)) {
2844
if (flags & BOLDATTR(screen)) {
2845
cgsId = gcBoldReverse;
2847
cgsId = gcNormReverse;
2849
EXCHANGE(fg_pix, bg_pix, xx_pix);
2851
if (flags & BOLDATTR(screen)) {
2858
2937
#if OPT_BLINK_TEXT
2859
2938
if ((screen->blink_state == ON) && (!screen->blink_as_bold) && (flags & BLINK)) {
2860
2939
fg_pix = bg_pix;
3252
3331
* old runtime configurations which yield incomplete or inaccurate data.
3255
systemWcwidthOk(void)
3334
systemWcwidthOk(int samplesize, int samplepass)
3261
for (n = 0; n < last; ++n) {
3339
for (n = 0; n < samplesize; ++n) {
3262
3340
int system_code = wcwidth(n);
3263
3341
int intern_code = mk_wcwidth(n);
3287
TRACE(("systemWcwidthOk: %d/%d mismatches\n", oops, last));
3288
return (oops < (last / 4));
3365
TRACE(("systemWcwidthOk: %d/%d mismatches, allowed %d\n",
3366
oops, samplesize, samplepass));
3367
return (oops <= samplepass);
3290
3369
#endif /* HAVE_WCWIDTH */
3293
decode_wcwidth(int mode)
3372
decode_wcwidth(int mode, int samplesize, int samplepass)
3295
3374
switch (mode) {
3297
3376
#if defined(HAVE_WCHAR_H) && defined(HAVE_WCWIDTH)
3298
if (xtermEnvUTF8() && systemWcwidthOk()) {
3377
if (xtermEnvUTF8() && systemWcwidthOk(samplesize, samplepass)) {
3299
3378
my_wcwidth = wcwidth;
3300
3379
TRACE(("using system wcwidth() function\n"));
3306
3388
my_wcwidth = &mk_wcwidth;
3307
3389
TRACE(("using MK wcwidth() function\n"));