Mercurial > emacs
comparison src/w32term.c @ 90834:3cc94105baca
[USE_FONT_BACKEND]:
(x_get_font_repertory, note_mouse_movement, x_set_mouse_face_gc):
(x_set_glyph_string_clipping, x_set_glyph_string_clipping_exactly):
(x_draw_glyph_string, x_draw_glyph_string_foreground):
(x_draw_composite_glyph_string_foreground, x_new_fontset2):
(x_free_frame_resources): Sync with xterm.c.
author | Jason Rumney <jasonr@gnu.org> |
---|---|
date | Tue, 01 May 2007 10:10:26 +0000 |
parents | dd7c098af727 |
children | 129b35b0274f |
comparison
equal
deleted
inserted
replaced
90833:3816faf8a124 | 90834:3cc94105baca |
---|---|
57 #include "keymap.h" | 57 #include "keymap.h" |
58 | 58 |
59 #include "w32heap.h" | 59 #include "w32heap.h" |
60 #include "w32bdf.h" | 60 #include "w32bdf.h" |
61 #include <shellapi.h> | 61 #include <shellapi.h> |
62 | |
63 #ifdef USE_FONT_BACKEND | |
64 #include "font.h" | |
65 #endif /* USE_FONT_BACKEND */ | |
62 | 66 |
63 #define abs(x) ((x) < 0 ? -(x) : (x)) | 67 #define abs(x) ((x) < 0 ? -(x) : (x)) |
64 | 68 |
65 | 69 |
66 /* Fringe bitmaps. */ | 70 /* Fringe bitmaps. */ |
1218 struct font_info *font_info; | 1222 struct font_info *font_info; |
1219 { | 1223 { |
1220 XFontStruct *font = (XFontStruct *) font_info->font; | 1224 XFontStruct *font = (XFontStruct *) font_info->font; |
1221 Lisp_Object table; | 1225 Lisp_Object table; |
1222 int min_byte1, max_byte1, min_byte2, max_byte2; | 1226 int min_byte1, max_byte1, min_byte2, max_byte2; |
1227 int c; | |
1228 struct charset *charset = CHARSET_FROM_ID (font_info->charset); | |
1229 int offset = CHARSET_OFFSET (charset); | |
1223 | 1230 |
1224 table = Fmake_char_table (Qnil, Qnil); | 1231 table = Fmake_char_table (Qnil, Qnil); |
1225 | 1232 |
1226 if (!font->bdf && pfnGetFontUnicodeRanges) | 1233 if (!font->bdf && pfnGetFontUnicodeRanges) |
1227 { | 1234 { |
1272 min_byte2 = font->min_char_or_byte2; | 1279 min_byte2 = font->min_char_or_byte2; |
1273 max_byte2 = font->max_char_or_byte2; | 1280 max_byte2 = font->max_char_or_byte2; |
1274 if (min_byte1 == 0 && max_byte1 == 0) | 1281 if (min_byte1 == 0 && max_byte1 == 0) |
1275 { | 1282 { |
1276 if (! font->per_char || font->all_chars_exist == True) | 1283 if (! font->per_char || font->all_chars_exist == True) |
1277 char_table_set_range (table, min_byte2, max_byte2, Qt); | 1284 { |
1285 if (offset >= 0) | |
1286 char_table_set_range (table, offset + min_byte2, | |
1287 offset + max_byte2, Qt); | |
1288 else | |
1289 for (; min_byte2 <= max_byte2; min_byte2++) | |
1290 { | |
1291 c = DECODE_CHAR (charset, min_byte2); | |
1292 CHAR_TABLE_SET (table, c, Qt); | |
1293 } | |
1294 } | |
1278 else | 1295 else |
1279 { | 1296 { |
1280 XCharStruct *pcm = font->per_char; | 1297 XCharStruct *pcm = font->per_char; |
1281 int from = -1; | 1298 int from = -1; |
1282 int i; | 1299 int i; |
1285 { | 1302 { |
1286 if (pcm->width == 0 && pcm->rbearing == pcm->lbearing) | 1303 if (pcm->width == 0 && pcm->rbearing == pcm->lbearing) |
1287 { | 1304 { |
1288 if (from >= 0) | 1305 if (from >= 0) |
1289 { | 1306 { |
1290 char_table_set_range (table, from, i - 1, Qt); | 1307 if (offset >= 0) |
1308 char_table_set_range (table, offset + from, | |
1309 offset + i - 1, Qt); | |
1310 else | |
1311 for (; from < i; from++) | |
1312 { | |
1313 c = DECODE_CHAR (charset, from); | |
1314 CHAR_TABLE_SET (table, c, Qt); | |
1315 } | |
1291 from = -1; | 1316 from = -1; |
1292 } | 1317 } |
1293 } | 1318 } |
1294 else if (from < 0) | 1319 else if (from < 0) |
1295 from = i; | 1320 from = i; |
1296 } | 1321 } |
1297 if (from >= 0) | 1322 if (from >= 0) |
1298 char_table_set_range (table, from, i - 1, Qt); | 1323 { |
1324 if (offset >= 0) | |
1325 char_table_set_range (table, offset + from, offset + i - 1, | |
1326 Qt); | |
1327 else | |
1328 for (; from < i; from++) | |
1329 { | |
1330 c = DECODE_CHAR (charset, from); | |
1331 CHAR_TABLE_SET (table, c, Qt); | |
1332 } | |
1333 } | |
1299 } | 1334 } |
1300 } | 1335 } |
1301 else | 1336 else |
1302 { | 1337 { |
1303 if (! font->per_char || font->all_chars_exist == True) | 1338 if (! font->per_char || font->all_chars_exist == True) |
1304 { | 1339 { |
1305 int i; | 1340 int i, j; |
1306 | 1341 |
1307 for (i = min_byte1; i <= max_byte1; i++) | 1342 if (offset >= 0) |
1308 char_table_set_range (table, | 1343 for (i = min_byte1; i <= max_byte1; i++) |
1309 (i << 8) | min_byte2, (i << 8) | max_byte2, | 1344 char_table_set_range |
1310 Qt); | 1345 (table, offset + ((i << 8) | min_byte2), |
1346 offset + ((i << 8) | max_byte2), Qt); | |
1347 else | |
1348 for (i = min_byte1; i <= max_byte1; i++) | |
1349 for (j = min_byte2; j <= max_byte2; j++) | |
1350 { | |
1351 unsiged code = (i << 8) | j; | |
1352 c = DECODE_CHAR (charset, code); | |
1353 CHAR_TABLE_SET (table, c, Qt); | |
1354 } | |
1311 } | 1355 } |
1312 else | 1356 else |
1313 { | 1357 { |
1314 XCharStruct *pcm = font->per_char; | 1358 XCharStruct *pcm = font->per_char; |
1315 int i; | 1359 int i; |
1323 { | 1367 { |
1324 if (pcm->width == 0 && pcm->rbearing == pcm->lbearing) | 1368 if (pcm->width == 0 && pcm->rbearing == pcm->lbearing) |
1325 { | 1369 { |
1326 if (from >= 0) | 1370 if (from >= 0) |
1327 { | 1371 { |
1328 char_table_set_range (table, (i << 8) | from, | 1372 if (offset >= 0) |
1329 (i << 8) | (j - 1), Qt); | 1373 char_table_set_range |
1374 (table, offset + ((i << 8) | from), | |
1375 offset + ((i << 8) | (j - 1)), Qt); | |
1376 else | |
1377 { | |
1378 for (; from < j; from++) | |
1379 { | |
1380 unsigned code = (i << 8) | from; | |
1381 c = ENCODE_CHAR (charset, code); | |
1382 CHAR_TABLE_SET (table, c, Qt); | |
1383 } | |
1384 } | |
1330 from = -1; | 1385 from = -1; |
1331 } | 1386 } |
1332 } | 1387 } |
1333 else if (from < 0) | 1388 else if (from < 0) |
1334 from = j; | 1389 from = j; |
1335 } | 1390 } |
1336 if (from >= 0) | 1391 if (from >= 0) |
1337 char_table_set_range (table, (i << 8) | from, | 1392 { |
1338 (i << 8) | (j - 1), Qt); | 1393 if (offset >= 0) |
1394 char_table_set_range | |
1395 (table, offset + ((i << 8) | from), | |
1396 offset + ((i << 8) | (j - 1)), Qt); | |
1397 else | |
1398 { | |
1399 for (; from < j; from++) | |
1400 { | |
1401 unsigned code = (i << 8) | from; | |
1402 c = DECODE_CHAR (charset, code); | |
1403 CHAR_TABLE_SET (table, c, Qt); | |
1404 } | |
1405 } | |
1406 } | |
1339 } | 1407 } |
1340 } | 1408 } |
1341 } | 1409 } |
1342 #endif | 1410 #endif |
1343 return table; | 1411 return table; |
1479 PREPARE_FACE_FOR_DISPLAY (s->f, s->face); | 1547 PREPARE_FACE_FOR_DISPLAY (s->f, s->face); |
1480 | 1548 |
1481 /* If font in this face is same as S->font, use it. */ | 1549 /* If font in this face is same as S->font, use it. */ |
1482 if (s->font == s->face->font) | 1550 if (s->font == s->face->font) |
1483 s->gc = s->face->gc; | 1551 s->gc = s->face->gc; |
1552 #ifdef USE_FONT_BACKEND | |
1553 else if (enable_font_backend) | |
1554 /* No need of setting a font for s->gc. */ | |
1555 s->gc = s->face->gc; | |
1556 #endif /* USE_FONT_BACKEND */ | |
1484 else | 1557 else |
1485 { | 1558 { |
1486 /* Otherwise construct scratch_cursor_gc with values from FACE | 1559 /* Otherwise construct scratch_cursor_gc with values from FACE |
1487 but font FONT. */ | 1560 but font FONT. */ |
1488 XGCValues xgcv; | 1561 XGCValues xgcv; |
1575 struct glyph_string *s; | 1648 struct glyph_string *s; |
1576 { | 1649 { |
1577 RECT r; | 1650 RECT r; |
1578 get_glyph_string_clip_rect (s, &r); | 1651 get_glyph_string_clip_rect (s, &r); |
1579 w32_set_clip_rectangle (s->hdc, &r); | 1652 w32_set_clip_rectangle (s->hdc, &r); |
1580 } | 1653 #ifdef USE_FONT_BACKEND |
1581 | 1654 s->clip_x = r.left, s->clip_y = r.top; |
1655 s->clip_width = r.right - r.left, s->clip_height = r.bottom - r.top; | |
1656 #endif /* USE_FONT_BACKEND */ | |
1657 } | |
1658 | |
1659 /* Set SRC's clipping for output of glyph string DST. This is called | |
1660 when we are drawing DST's left_overhang or right_overhang only in | |
1661 the area of SRC. */ | |
1662 | |
1663 static void | |
1664 x_set_glyph_string_clipping_exactly (src, dst) | |
1665 struct glyph_string *src, *dst; | |
1666 { | |
1667 RECT r; | |
1668 | |
1669 #ifdef USE_FONT_BACKEND | |
1670 if (enable_font_backend) | |
1671 { | |
1672 r.left = dst->clip_x = src->x; | |
1673 r.right = r.left + (dst->clip_width = src->width); | |
1674 r.top = dst->clip_y = src->y; | |
1675 r.bottom = r.top + (dst->clip_height = src->height); | |
1676 } | |
1677 else | |
1678 { | |
1679 #endif /* USE_FONT_BACKEND */ | |
1680 struct glyph_string *clip_head = src->clip_head; | |
1681 struct glyph_string *clip_tail = src->clip_tail; | |
1682 | |
1683 /* This foces clipping just this glyph string. */ | |
1684 src->clip_head = src->clip_tail = src; | |
1685 get_glyph_string_clip_rect (src, &r); | |
1686 src->clip_head = clip_head, src->clip_tail = clip_tail; | |
1687 #ifdef USE_FONT_BACKEND | |
1688 } | |
1689 #endif /* USE_FONT_BACKEND */ | |
1690 w32_set_clip_rectangle (dst->hdc, &r); | |
1691 } | |
1582 | 1692 |
1583 /* RIF: | 1693 /* RIF: |
1584 Compute left and right overhang of glyph string S. If S is a glyph | 1694 Compute left and right overhang of glyph string S. If S is a glyph |
1585 string for a composition, assume overhangs don't exist. */ | 1695 string for a composition, assume overhangs don't exist. */ |
1586 | 1696 |
1721 w32_draw_rectangle (s->hdc, s->gc, x, s->y, g->pixel_width - 1, | 1831 w32_draw_rectangle (s->hdc, s->gc, x, s->y, g->pixel_width - 1, |
1722 s->height - 1); | 1832 s->height - 1); |
1723 x += g->pixel_width; | 1833 x += g->pixel_width; |
1724 } | 1834 } |
1725 } | 1835 } |
1836 #ifdef USE_FONT_BACKEND | |
1837 else if (enable_font_backend) | |
1838 { | |
1839 unsigned *code = alloca (sizeof (unsigned) * s->nchars); | |
1840 int boff = s->font_info->baseline_offset; | |
1841 struct font *font = (struct font *) s->font_info; | |
1842 int y; | |
1843 | |
1844 for (i = 0; i < s->nchars; i++) | |
1845 code[i] = (s->char2b[i].byte1 << 8) | s->char2b[i].byte2; | |
1846 | |
1847 if (s->font_info->vertical_centering) | |
1848 boff = VCENTER_BASELINE_OFFSET (s->font, s->f) - boff; | |
1849 | |
1850 y = s->ybase - boff; | |
1851 if (s->for_overlaps | |
1852 || (s->background_filled_p && s->hl != DRAW_CURSOR)) | |
1853 font->driver->draw (s, 0, s->nchars, x, y, 0); | |
1854 else | |
1855 font->driver->draw (s, 0, s->nchars, x, y, 1); | |
1856 if (s->face->overstrike) | |
1857 font->driver->draw (s, 0, s->nchars, x + 1, y, 0); | |
1858 } | |
1859 #endif /* USE_FONT_BACKEND */ | |
1726 else | 1860 else |
1727 { | 1861 { |
1728 char *char1b = (char *) s->char2b; | 1862 char *char1b = (char *) s->char2b; |
1729 int boff = s->font_info->baseline_offset; | 1863 int boff = s->font_info->baseline_offset; |
1730 | 1864 |
1757 | 1891 |
1758 static void | 1892 static void |
1759 x_draw_composite_glyph_string_foreground (s) | 1893 x_draw_composite_glyph_string_foreground (s) |
1760 struct glyph_string *s; | 1894 struct glyph_string *s; |
1761 { | 1895 { |
1762 int i, x; | 1896 int i, j, x; |
1763 HFONT old_font; | 1897 HFONT old_font; |
1764 | 1898 |
1765 /* If first glyph of S has a left box line, start drawing the text | 1899 /* If first glyph of S has a left box line, start drawing the text |
1766 of S to the right of that box line. */ | 1900 of S to the right of that box line. */ |
1767 if (s->face->box != FACE_NO_BOX | 1901 if (s->face && s->face->box != FACE_NO_BOX |
1768 && s->first_glyph->left_box_line_p) | 1902 && s->first_glyph->left_box_line_p) |
1769 x = s->x + abs (s->face->box_line_width); | 1903 x = s->x + abs (s->face->box_line_width); |
1770 else | 1904 else |
1771 x = s->x; | 1905 x = s->x; |
1772 | 1906 |
1789 { | 1923 { |
1790 if (s->gidx == 0) | 1924 if (s->gidx == 0) |
1791 w32_draw_rectangle (s->hdc, s->gc, x, s->y, s->width - 1, | 1925 w32_draw_rectangle (s->hdc, s->gc, x, s->y, s->width - 1, |
1792 s->height - 1); | 1926 s->height - 1); |
1793 } | 1927 } |
1928 #ifdef USE_FONT_BACKEND | |
1929 else if (enable_font_backend) | |
1930 { | |
1931 struct font *font = (struct font *) s->font_info; | |
1932 int y = s->ybase; | |
1933 int width = 0; | |
1934 | |
1935 if (s->cmp->method == COMPOSITION_WITH_GLYPH_STRING) | |
1936 { | |
1937 Lisp_Object gstring = AREF (XHASH_TABLE (composition_hash_table) | |
1938 ->key_and_value, | |
1939 s->cmp->hash_index * 2); | |
1940 int from; | |
1941 | |
1942 for (i = from = 0; i < s->nchars; i++) | |
1943 { | |
1944 Lisp_Object g = LGSTRING_GLYPH (gstring, i); | |
1945 Lisp_Object adjustment = LGLYPH_ADJUSTMENT (g); | |
1946 int xoff, yoff, wadjust; | |
1947 | |
1948 if (! VECTORP (adjustment)) | |
1949 { | |
1950 width += XINT (LGLYPH_WIDTH (g)); | |
1951 continue; | |
1952 } | |
1953 if (from < i) | |
1954 { | |
1955 font->driver->draw (s, from, i, x, y, 0); | |
1956 x += width; | |
1957 } | |
1958 xoff = XINT (AREF (adjustment, 0)); | |
1959 yoff = XINT (AREF (adjustment, 1)); | |
1960 wadjust = XINT (AREF (adjustment, 2)); | |
1961 | |
1962 font->driver->draw (s, i, i + 1, x + xoff, y + yoff, 0); | |
1963 x += XINT (LGLYPH_WIDTH (g)) + wadjust; | |
1964 from = i + 1; | |
1965 width = 0; | |
1966 } | |
1967 if (from < i) | |
1968 font->driver->draw (s, from, i, x, y, 0); | |
1969 } | |
1970 else | |
1971 { | |
1972 for (i = 0, j = s->gidx; i < s->nchars; i++, j++) | |
1973 if (COMPOSITION_GLYPH (s->cmp, j) != '\t') | |
1974 { | |
1975 int xx = x + s->cmp->offsets[j * 2]; | |
1976 int yy = y - s->cmp->offsets[j * 2 + 1]; | |
1977 | |
1978 font->driver->draw (s, j, j + 1, xx, yy, 0); | |
1979 if (s->face->overstrike) | |
1980 font->driver->draw (s, j, j + 1, xx + 1, yy, 0); | |
1981 } | |
1982 } | |
1983 } | |
1984 #endif /* USE_FONT_BACKEND */ | |
1794 else | 1985 else |
1795 { | 1986 { |
1796 for (i = 0; i < s->nchars; i++, ++s->gidx) | 1987 for (i = 0, j = s->gidx; i < s->nchars; i++, j++) |
1797 { | 1988 if (s->face) |
1798 w32_text_out (s, x + s->cmp->offsets[s->gidx * 2], | 1989 { |
1799 s->ybase - s->cmp->offsets[s->gidx * 2 + 1], | 1990 w32_text_out (s, x + s->cmp->offsets[j * 2], |
1800 s->char2b + i, 1); | 1991 s->ybase - s->cmp->offsets[j * 2 + 1], |
1801 if (s->face->overstrike) | 1992 s->char2b + j, 1); |
1802 w32_text_out (s, x + s->cmp->offsets[s->gidx * 2] + 1, | 1993 if (s->face->overstrike) |
1803 s->ybase - s->cmp->offsets[s->gidx * 2 + 1], | 1994 w32_text_out (s, x + s->cmp->offsets[j * 2] + 1, |
1804 s->char2b + i, 1); | 1995 s->ybase - s->cmp->offsets[j + 1], |
1805 } | 1996 s->char2b + j, 1); |
1997 } | |
1806 } | 1998 } |
1807 | 1999 |
1808 if (s->font && s->font->hfont) | 2000 if (s->font && s->font->hfont) |
1809 SelectObject (s->hdc, old_font); | 2001 SelectObject (s->hdc, old_font); |
1810 } | 2002 } |
2603 /* If S draws into the background of its successor, draw the | 2795 /* If S draws into the background of its successor, draw the |
2604 background of the successor first so that S can draw into it. | 2796 background of the successor first so that S can draw into it. |
2605 This makes S->next use XDrawString instead of XDrawImageString. */ | 2797 This makes S->next use XDrawString instead of XDrawImageString. */ |
2606 if (s->next && s->right_overhang && !s->for_overlaps) | 2798 if (s->next && s->right_overhang && !s->for_overlaps) |
2607 { | 2799 { |
2608 xassert (s->next->img == NULL); | 2800 int width; |
2609 x_set_glyph_string_gc (s->next); | 2801 struct glyph_string *next; |
2610 x_set_glyph_string_clipping (s->next); | 2802 for (width = 0, next = s->next; next; |
2611 x_draw_glyph_string_background (s->next, 1); | 2803 width += next->width, next = next->next) |
2804 if (next->first_glyph->type != IMAGE_GLYPH) | |
2805 { | |
2806 x_set_glyph_string_gc (next); | |
2807 x_set_glyph_string_clipping (next); | |
2808 x_draw_glyph_string_background (next, 1); | |
2809 #ifdef USE_FONT_BACKEND | |
2810 next->clip_width = 0; | |
2811 #endif /* USE_FONT_BACKEND */ | |
2812 } | |
2612 } | 2813 } |
2613 | 2814 |
2614 /* Set up S->gc, set clipping and draw S. */ | 2815 /* Set up S->gc, set clipping and draw S. */ |
2615 x_set_glyph_string_gc (s); | 2816 x_set_glyph_string_gc (s); |
2616 | 2817 |
2626 x_draw_glyph_string_background (s, 1); | 2827 x_draw_glyph_string_background (s, 1); |
2627 x_draw_glyph_string_box (s); | 2828 x_draw_glyph_string_box (s); |
2628 x_set_glyph_string_clipping (s); | 2829 x_set_glyph_string_clipping (s); |
2629 relief_drawn_p = 1; | 2830 relief_drawn_p = 1; |
2630 } | 2831 } |
2832 else if ((s->prev && s->prev->hl != s->hl && s->left_overhang) | |
2833 || (s->next && s->next->hl != s->hl && s->right_overhang)) | |
2834 /* We must clip just this glyph. left_overhang part has already | |
2835 drawn when s->prev was drawn, and right_overhang part will be | |
2836 drawn later when s->next is drawn. */ | |
2837 x_set_glyph_string_clipping_exactly (s, s); | |
2631 else | 2838 else |
2632 x_set_glyph_string_clipping (s); | 2839 x_set_glyph_string_clipping (s); |
2633 | 2840 |
2634 switch (s->first_glyph->type) | 2841 switch (s->first_glyph->type) |
2635 { | 2842 { |
2665 { | 2872 { |
2666 /* Draw underline. */ | 2873 /* Draw underline. */ |
2667 if (s->face->underline_p | 2874 if (s->face->underline_p |
2668 && (s->font->bdf || !s->font->tm.tmUnderlined)) | 2875 && (s->font->bdf || !s->font->tm.tmUnderlined)) |
2669 { | 2876 { |
2670 unsigned long h = 1; | 2877 unsigned long h; |
2671 unsigned long dy = 0; | 2878 unsigned long dy = 0; |
2672 | 2879 /* Get the underline thickness. Default is 1 pixel. */ |
2673 if (x_underline_at_descent_line) | 2880 #ifdef USE_FONT_BACKEND |
2674 dy = s->height - h; | 2881 if (enable_font_backend) |
2675 else | 2882 /* In the future, we must use information of font. */ |
2883 h = 1; | |
2884 else | |
2885 #endif /* USE_FONT_BACKEND */ | |
2886 h = 1; | |
2887 | |
2888 #ifdef USE_FONT_BACKEND | |
2889 if (enable_font_backend) | |
2890 { | |
2891 if (s->face->font) | |
2892 /* In the future, we must use information of font. */ | |
2893 y = s->ybase + (s->face->font->max_bounds.descent + 1) / 2; | |
2894 else | |
2895 y = s->y + s->height - h; | |
2896 } | |
2897 else | |
2898 #endif | |
2676 { | 2899 { |
2677 /* TODO: Use font information for positioning and thickness of | 2900 if (x_underline_at_descent_line) |
2678 underline. See OUTLINETEXTMETRIC, and xterm.c. Note: If | 2901 dy = s->height - h; |
2679 you make this work, don't forget to change the doc string of | 2902 else |
2680 x-use-underline-position-properties below. */ | 2903 { |
2681 dy = s->height - h; | 2904 /* TODO: Use font information for positioning and |
2905 thickness of underline. See OUTLINETEXTMETRIC, | |
2906 and xterm.c. Note: If you makedev this work, | |
2907 don't forget to change the doc string of | |
2908 x-use-underline_color-position-properties | |
2909 below. */ | |
2910 dy = s->height - h; | |
2911 } | |
2682 } | 2912 } |
2683 if (s->face->underline_defaulted_p) | 2913 if (s->face->underline_defaulted_p) |
2684 { | 2914 { |
2685 w32_fill_area (s->f, s->hdc, s->gc->foreground, s->x, | 2915 w32_fill_area (s->f, s->hdc, s->gc->foreground, s->x, |
2686 s->y + dy, s->background_width, 1); | 2916 s->y + dy, s->background_width, 1); |
2689 { | 2919 { |
2690 w32_fill_area (s->f, s->hdc, s->face->underline_color, s->x, | 2920 w32_fill_area (s->f, s->hdc, s->face->underline_color, s->x, |
2691 s->y + dy, s->background_width, 1); | 2921 s->y + dy, s->background_width, 1); |
2692 } | 2922 } |
2693 } | 2923 } |
2694 | |
2695 /* Draw overline. */ | 2924 /* Draw overline. */ |
2696 if (s->face->overline_p) | 2925 if (s->face->overline_p) |
2697 { | 2926 { |
2698 unsigned long dy = 0, h = 1; | 2927 unsigned long dy = 0, h = 1; |
2699 | 2928 |
2700 if (s->face->overline_color_defaulted_p) | 2929 if (s->face->overline_color_defaulted_p) |
2701 { | 2930 { |
2702 w32_fill_area (s->f, s->hdc, s->gc->foreground, s->x, | 2931 w32_fill_area (s->f, s->hdc, s->gc->foreground, s->x, |
2703 s->y + dy, s->background_width, h); | 2932 s->y + dy, s->background_width, h); |
2704 } | 2933 } |
2705 else | 2934 else |
2706 { | 2935 { |
2707 w32_fill_area (s->f, s->hdc, s->face->overline_color, s->x, | 2936 w32_fill_area (s->f, s->hdc, s->face->overline_color, s->x, |
2708 s->y + dy, s->background_width, h); | 2937 s->y + dy, s->background_width, h); |
2709 } | 2938 } |
2726 w32_fill_area (s->f, s->hdc, s->face->underline_color, s->x, | 2955 w32_fill_area (s->f, s->hdc, s->face->underline_color, s->x, |
2727 s->y + dy, s->width, h); | 2956 s->y + dy, s->width, h); |
2728 } | 2957 } |
2729 } | 2958 } |
2730 | 2959 |
2731 /* Draw relief. */ | 2960 /* Draw relief if not yet drawn. */ |
2732 if (!relief_drawn_p && s->face->box != FACE_NO_BOX) | 2961 if (!relief_drawn_p && s->face->box != FACE_NO_BOX) |
2733 x_draw_glyph_string_box (s); | 2962 x_draw_glyph_string_box (s); |
2963 | |
2964 if (s->prev) | |
2965 { | |
2966 struct glyph_string *prev; | |
2967 | |
2968 for (prev = s->prev; prev; prev = prev->prev) | |
2969 if (prev->hl != s->hl | |
2970 && prev->x + prev->width + prev->right_overhang > s->x) | |
2971 { | |
2972 /* As prev was drawn while clipped to its own area, we | |
2973 must draw the right_overhang part using s->hl now. */ | |
2974 enum draw_glyphs_face save = prev->hl; | |
2975 | |
2976 prev->hl = s->hl; | |
2977 x_set_glyph_string_gc (prev); | |
2978 x_set_glyph_string_clipping_exactly (s, prev); | |
2979 if (prev->first_glyph->type == CHAR_GLYPH) | |
2980 x_draw_glyph_string_foreground (prev); | |
2981 else | |
2982 x_draw_composite_glyph_string_foreground (prev); | |
2983 w32_set_clip_rectangle (prev->hdc, NULL); | |
2984 prev->hl = save; | |
2985 #ifdef USE_FONT_BACKEND | |
2986 prev->clip_width = 0; | |
2987 #endif /* USE_FONT_BACKEND */ | |
2988 } | |
2989 } | |
2990 | |
2991 if (s->next) | |
2992 { | |
2993 struct glyph_string *next; | |
2994 | |
2995 for (next = s->next; next; next = next->next) | |
2996 if (next->hl != s->hl | |
2997 && next->x - next->left_overhang < s->x + s->width) | |
2998 { | |
2999 /* As next will be drawn while clipped to its own area, | |
3000 we must draw the left_overhang part using s->hl now. */ | |
3001 enum draw_glyphs_face save = next->hl; | |
3002 | |
3003 next->hl = s->hl; | |
3004 x_set_glyph_string_gc (next); | |
3005 x_set_glyph_string_clipping_exactly (s, next); | |
3006 if (next->first_glyph->type == CHAR_GLYPH) | |
3007 x_draw_glyph_string_foreground (next); | |
3008 else | |
3009 x_draw_composite_glyph_string_foreground (next); | |
3010 w32_set_clip_rectangle (next->hdc, NULL); | |
3011 next->hl = save; | |
3012 #ifdef USE_FONT_BACKEND | |
3013 next->clip_width = 0; | |
3014 #endif /* USE_FONT_BACKEND */ | |
3015 } | |
3016 } | |
2734 } | 3017 } |
2735 | 3018 |
2736 /* Reset clipping. */ | 3019 /* Reset clipping. */ |
2737 w32_set_clip_rectangle (s->hdc, NULL); | 3020 w32_set_clip_rectangle (s->hdc, NULL); |
3021 #ifdef USE_FONT_BACKEND | |
3022 s->clip_width = 0; | |
3023 #endif /* USE_FONT_BACKEND */ | |
2738 } | 3024 } |
2739 | 3025 |
2740 | 3026 |
2741 /* Shift display to make room for inserted glyphs. */ | 3027 /* Shift display to make room for inserted glyphs. */ |
2742 | 3028 |
3377 | 3663 |
3378 last_mouse_movement_time = msg->time; | 3664 last_mouse_movement_time = msg->time; |
3379 memcpy (&last_mouse_motion_event, msg, sizeof (last_mouse_motion_event)); | 3665 memcpy (&last_mouse_motion_event, msg, sizeof (last_mouse_motion_event)); |
3380 XSETFRAME (last_mouse_motion_frame, frame); | 3666 XSETFRAME (last_mouse_motion_frame, frame); |
3381 | 3667 |
3668 if (!FRAME_X_OUTPUT (frame)) | |
3669 return 0; | |
3670 | |
3382 if (msg->hwnd != FRAME_W32_WINDOW (frame)) | 3671 if (msg->hwnd != FRAME_W32_WINDOW (frame)) |
3383 { | 3672 { |
3384 frame->mouse_moved = 1; | 3673 frame->mouse_moved = 1; |
3385 last_mouse_scroll_bar = Qnil; | 3674 last_mouse_scroll_bar = Qnil; |
3386 note_mouse_highlight (frame, -1, -1); | 3675 note_mouse_highlight (frame, -1, -1); |
5492 FRAME_FONTSET(f) = fontset; | 5781 FRAME_FONTSET(f) = fontset; |
5493 | 5782 |
5494 return fontset_name (fontset); | 5783 return fontset_name (fontset); |
5495 } | 5784 } |
5496 | 5785 |
5786 #ifdef USE_FONT_BACKEND | |
5787 Lisp_Object | |
5788 x_new_fontset2 (f, fontset, font_object) | |
5789 struct frame *f; | |
5790 int fontset; | |
5791 Lisp_Object font_object; | |
5792 { | |
5793 struct font *font = XSAVE_VALUE (font_object)->pointer; | |
5794 | |
5795 if (FRAME_FONT_OBJECT (f) == font) | |
5796 /* This font is already set in frame F. There's nothing more to | |
5797 do. */ | |
5798 return fontset_name (fontset); | |
5799 | |
5800 BLOCK_INPUT; | |
5801 | |
5802 FRAME_FONT_OBJECT (f) = font; | |
5803 FRAME_FONT (f) = font->font.font; | |
5804 FRAME_BASELINE_OFFSET (f) = font->font.baseline_offset; | |
5805 FRAME_FONTSET (f) = fontset; | |
5806 | |
5807 FRAME_COLUMN_WIDTH (f) = font->font.average_width; | |
5808 FRAME_SPACE_WIDTH (f) = font->font.space_width; | |
5809 FRAME_LINE_HEIGHT (f) = font->font.height; | |
5810 | |
5811 compute_fringe_widths (f, 1); | |
5812 | |
5813 /* Compute the scroll bar width in character columns. */ | |
5814 if (FRAME_CONFIG_SCROLL_BAR_WIDTH (f) > 0) | |
5815 { | |
5816 int wid = FRAME_COLUMN_WIDTH (f); | |
5817 FRAME_CONFIG_SCROLL_BAR_COLS (f) | |
5818 = (FRAME_CONFIG_SCROLL_BAR_WIDTH (f) + wid - 1) / wid; | |
5819 } | |
5820 else | |
5821 { | |
5822 int wid = FRAME_COLUMN_WIDTH (f); | |
5823 FRAME_CONFIG_SCROLL_BAR_COLS (f) = (14 + wid - 1) / wid; | |
5824 } | |
5825 | |
5826 /* Now make the frame display the given font. */ | |
5827 if (FRAME_X_WINDOW (f) != 0) | |
5828 { | |
5829 /* Don't change the size of a tip frame; there's no point in | |
5830 doing it because it's done in Fx_show_tip, and it leads to | |
5831 problems because the tip frame has no widget. */ | |
5832 if (NILP (tip_frame) || XFRAME (tip_frame) != f) | |
5833 x_set_window_size (f, 0, FRAME_COLS (f), FRAME_LINES (f)); | |
5834 } | |
5835 | |
5836 #ifdef HAVE_X_I18N | |
5837 if (FRAME_XIC (f) | |
5838 && (FRAME_XIC_STYLE (f) & (XIMPreeditPosition | XIMStatusArea))) | |
5839 xic_set_xfontset (f, SDATA (fontset_ascii (fontset))); | |
5840 #endif | |
5841 | |
5842 UNBLOCK_INPUT; | |
5843 | |
5844 return fontset_name (fontset); | |
5845 } | |
5846 #endif /* USE_FONT_BACKEND */ | |
5847 | |
5497 | 5848 |
5498 /*********************************************************************** | 5849 /*********************************************************************** |
5499 TODO: W32 Input Methods | 5850 TODO: W32 Input Methods |
5500 ***********************************************************************/ | 5851 ***********************************************************************/ |
5501 /* Listing missing functions from xterm.c helps diff stay in step. | 5852 /* Listing missing functions from xterm.c helps diff stay in step. |
6030 struct frame *f; | 6381 struct frame *f; |
6031 { | 6382 { |
6032 struct w32_display_info *dpyinfo = FRAME_W32_DISPLAY_INFO (f); | 6383 struct w32_display_info *dpyinfo = FRAME_W32_DISPLAY_INFO (f); |
6033 | 6384 |
6034 BLOCK_INPUT; | 6385 BLOCK_INPUT; |
6386 | |
6387 #ifdef USE_FONT_BACKEND | |
6388 /* We must free faces before destroying windows because some | |
6389 font-driver (e.g. xft) access a window while finishing a | |
6390 face. */ | |
6391 if (enable_font_backend | |
6392 && FRAME_FACE_CACHE (f)) | |
6393 free_frame_faces (f); | |
6394 #endif /* USE_FONT_BACKEND */ | |
6035 | 6395 |
6036 if (FRAME_W32_WINDOW (f)) | 6396 if (FRAME_W32_WINDOW (f)) |
6037 my_destroy_window (f, FRAME_W32_WINDOW (f)); | 6397 my_destroy_window (f, FRAME_W32_WINDOW (f)); |
6038 | 6398 |
6039 free_frame_menubar (f); | 6399 free_frame_menubar (f); |