comparison src/ftxfont.c @ 90554:d0351223b22a

(ftxfont_create_gcs): New function. (ftxfont_draw_bitmap): Fix arg to ftfont_driver.get_bitmap. (ftxfont_draw_backgrond): Fix filling region. (ftxfont_default_fid): New function. (ftxfont_open): Set xfotn->fid to the return value of ftxfont_default_fid. (ftxfont_prepare_face): Use ftxfont_create_gcs to create GCs. (ftxfont_done_face): Free only GCs that are created by ftxfont_create_gcs. (ftxfont_draw): If face->gc != s->gc, create proper GCs.
author Kenichi Handa <handa@m17n.org>
date Fri, 28 Jul 2006 12:44:45 +0000
parents ddb25860d044
children c443c8a56b84
comparison
equal deleted inserted replaced
90553:0265187804a5 90554:d0351223b22a
38 /* FTX font driver. */ 38 /* FTX font driver. */
39 39
40 static Lisp_Object Qftx; 40 static Lisp_Object Qftx;
41 41
42 /* Prototypes for helper function. */ 42 /* Prototypes for helper function. */
43 static int ftxfont_create_gcs P_ ((FRAME_PTR, GC *,
44 unsigned long, unsigned long));
43 static int ftxfont_draw_bitmap P_ ((FRAME_PTR, GC *, struct font *, unsigned, 45 static int ftxfont_draw_bitmap P_ ((FRAME_PTR, GC *, struct font *, unsigned,
44 int, int, XPoint *, int, int *n)); 46 int, int, XPoint *, int, int *n));
45 static void ftxfont_draw_backgrond P_ ((FRAME_PTR, struct font *, GC, 47 static void ftxfont_draw_backgrond P_ ((FRAME_PTR, struct font *, GC,
46 int, int, int)); 48 int, int, int));
49 static Font ftxfont_default_fid P_ ((FRAME_PTR));
50
51 /* Create 6 GCs for antialiasing by interpolating colors FOREGROUND
52 and BACKGROUND. GCS[0] is closest to BACKGROUND, and GCS[5] is
53 closest to FOREGROUND. */
54
55 static int
56 ftxfont_create_gcs (f, gcs, foreground, background)
57 FRAME_PTR f;
58 GC *gcs;
59 unsigned long foreground, background;
60 {
61 XColor colors[3];
62 XGCValues xgcv;
63 int i;
64
65 colors[0].pixel = foreground;
66 colors[1].pixel = background;
67
68 BLOCK_INPUT;
69 XQueryColors (FRAME_X_DISPLAY (f), FRAME_X_COLORMAP (f), colors, 2);
70 for (i = 1; i < 7; i++)
71 {
72 colors[2].red = (colors[0].red * i + colors[1].red * (8 - i)) / 8;
73 colors[2].green = (colors[0].green * i + colors[1].green * (8 - i)) / 8;
74 colors[2].blue = (colors[0].blue * i + colors[1].blue * (8 - i)) / 8;
75 if (! x_alloc_nearest_color (f, FRAME_X_COLORMAP (f), &colors[2]))
76 break;
77 xgcv.foreground = colors[2].pixel;
78 gcs[i - 1] = XCreateGC (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f),
79 GCForeground, &xgcv);
80 }
81 UNBLOCK_INPUT;
82
83 if (i < 7)
84 {
85 BLOCK_INPUT;
86 for (i--; i >= 0; i--)
87 XFreeGC (FRAME_X_DISPLAY (f), gcs[i]);
88 UNBLOCK_INPUT;
89 return -1;
90 }
91 return 0;
92 }
47 93
48 static int 94 static int
49 ftxfont_draw_bitmap (f, gc, font, code, x, y, p, size, n) 95 ftxfont_draw_bitmap (f, gc, font, code, x, y, p, size, n)
50 FRAME_PTR f; 96 FRAME_PTR f;
51 GC *gc; 97 GC *gc;
57 { 103 {
58 struct font_bitmap bitmap; 104 struct font_bitmap bitmap;
59 unsigned char *b; 105 unsigned char *b;
60 int i, j; 106 int i, j;
61 107
62 if (ftfont_driver.get_bitmap (font, code, &bitmap, 1) < 0) 108 if (ftfont_driver.get_bitmap (font, code, &bitmap, size > 0x100 ? 1 : 8) < 0)
63 return 0; 109 return 0;
64 for (i = 0, b = bitmap.buffer; i < bitmap.rows; 110 for (i = 0, b = bitmap.buffer; i < bitmap.rows;
65 i++, b += bitmap.pitch) 111 i++, b += bitmap.pitch)
66 { 112 {
67 if (size > 0x100) 113 if (size > 0x100)
119 165
120 XGetGCValues (FRAME_X_DISPLAY (f), gc, 166 XGetGCValues (FRAME_X_DISPLAY (f), gc,
121 GCForeground | GCBackground, &xgcv); 167 GCForeground | GCBackground, &xgcv);
122 XSetForeground (FRAME_X_DISPLAY (f), gc, xgcv.background); 168 XSetForeground (FRAME_X_DISPLAY (f), gc, xgcv.background);
123 XFillRectangle (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f), gc, 169 XFillRectangle (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f), gc,
124 x, y - font->ascent, width, font->font.height); 170 x, y - font->ascent, width, y + font->descent);
125 XSetForeground (FRAME_X_DISPLAY (f), gc, xgcv.foreground); 171 XSetForeground (FRAME_X_DISPLAY (f), gc, xgcv.foreground);
172 }
173
174 /* Return the default Font ID on frame F. */
175
176 static Font
177 ftxfont_default_fid (f)
178 FRAME_PTR f;
179 {
180 static int fid_known;
181 static Font fid;
182
183 if (! fid_known)
184 {
185 fid = XLoadFont (FRAME_X_DISPLAY (f), "fixed");
186 if (! fid)
187 {
188 fid = XLoadFont (FRAME_X_DISPLAY (f), "*");
189 if (! fid)
190 abort ();
191 }
192 fid_known = 1;
193 }
194 return fid;
126 } 195 }
127 196
128 /* Prototypes for font-driver methods. */ 197 /* Prototypes for font-driver methods. */
129 static Lisp_Object ftxfont_list P_ ((Lisp_Object, Lisp_Object)); 198 static Lisp_Object ftxfont_list P_ ((Lisp_Object, Lisp_Object));
130 static struct font *ftxfont_open P_ ((FRAME_PTR, Lisp_Object, int)); 199 static struct font *ftxfont_open P_ ((FRAME_PTR, Lisp_Object, int));
170 { 239 {
171 free (xfont); 240 free (xfont);
172 return NULL; 241 return NULL;
173 } 242 }
174 243
175 xfont->fid = FRAME_FONT (f)->fid; 244 xfont->fid = ftxfont_default_fid (f);
176 xfont->ascent = font->ascent; 245 xfont->ascent = font->ascent;
177 xfont->descent = font->descent; 246 xfont->descent = font->descent;
178 xfont->max_bounds.width = font->font.size; 247 xfont->max_bounds.width = font->font.size;
179 xfont->min_bounds.width = font->min_width; 248 xfont->min_bounds.width = font->min_width;
180 font->font.font = xfont; 249 font->font.font = xfont;
216 static int 285 static int
217 ftxfont_prepare_face (f, face) 286 ftxfont_prepare_face (f, face)
218 FRAME_PTR f; 287 FRAME_PTR f;
219 struct face *face; 288 struct face *face;
220 { 289 {
221 GC gc[6]; 290 struct font *font = (struct font *) face->font_info;
291 GC gcs[6];
222 XColor colors[3]; 292 XColor colors[3];
223 XGCValues xgcv; 293 XGCValues xgcv;
224 unsigned long mask = GCForeground | GCBackground | GCGraphicsExposures; 294 unsigned long mask = GCForeground | GCBackground | GCGraphicsExposures;
225 int i; 295 int i;
226 296
227 face->extra = NULL; 297 face->extra = NULL;
228 298
229 /* Here, we create 6 more GCs to simulate anti-aliasing. */ 299 if (! font->scalable)
230 BLOCK_INPUT; 300 return 0;
231 XGetGCValues (FRAME_X_DISPLAY (f), face->gc, mask, &xgcv); 301
232 colors[0].pixel = face->foreground; 302 if (ftxfont_create_gcs (f, gcs, face->foreground, face->background) < 0)
233 colors[1].pixel = face->background; 303 /* Give up antialiasing. */
234 XQueryColors (FRAME_X_DISPLAY (f), FRAME_X_COLORMAP (f), colors, 2); 304 return 0;
235 for (i = 1; i < 7; i++) 305
236 {
237 colors[2].red = (colors[0].red * i + colors[1].red * (7 - i)) / 7;
238 colors[2].green = (colors[0].green * i + colors[1].green * (7 - i)) / 7;
239 colors[2].blue = (colors[0].blue * i + colors[1].blue * (7 - i)) / 7;
240 if (! x_alloc_nearest_color (f, FRAME_X_COLORMAP (f), &colors[2]))
241 break;
242 xgcv.foreground = colors[2].pixel;
243 gc[i - 1] = XCreateGC (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f),
244 mask, &xgcv);
245 }
246 UNBLOCK_INPUT;
247
248 if (i < 7)
249 return -1;
250 face->extra = malloc (sizeof (GC) * 7); 306 face->extra = malloc (sizeof (GC) * 7);
251 if (! face->extra) 307 if (! face->extra)
252 return -1; 308 return -1;
253 for (i = 0; i < 6; i++) 309 for (i = 0; i < 6; i++)
254 ((GC *) face->extra)[i] = gc[i]; 310 ((GC *) face->extra)[i] = gcs[i];
255 ((GC *) face->extra)[i] = face->gc; 311 ((GC *) face->extra)[i] = face->gc;
256 return 0; 312 return 0;
257 } 313 }
258 314
259 static void 315 static void
264 if (face->extra) 320 if (face->extra)
265 { 321 {
266 int i; 322 int i;
267 323
268 BLOCK_INPUT; 324 BLOCK_INPUT;
269 for (i = 0; i < 7; i++) 325 for (i = 0; i < 6; i++)
270 XFreeGC (FRAME_X_DISPLAY (f), ((GC *) face->extra)[i]); 326 XFreeGC (FRAME_X_DISPLAY (f), ((GC *) face->extra)[i]);
271 UNBLOCK_INPUT; 327 UNBLOCK_INPUT;
272 free (face->extra); 328 free (face->extra);
273 face->extra = NULL; 329 face->extra = NULL;
274 } 330 }
279 struct glyph_string *s; 335 struct glyph_string *s;
280 int from, to, x, y, with_background; 336 int from, to, x, y, with_background;
281 { 337 {
282 FRAME_PTR f = s->f; 338 FRAME_PTR f = s->f;
283 struct face *face = s->face; 339 struct face *face = s->face;
284 struct font *font = (struct font *) face->font; 340 struct font *font = (struct font *) face->font_info;
285 XPoint p[0x700]; 341 XPoint p[0x700];
286 int n[7]; 342 int n[7];
287 unsigned *code; 343 unsigned *code;
288 int len = to - from; 344 int len = to - from;
289 int i; 345 int i;
346 GC *gcs;
290 347
291 n[0] = n[1] = n[2] = n[3] = n[4] = n[5] = n[6] = 0; 348 n[0] = n[1] = n[2] = n[3] = n[4] = n[5] = n[6] = 0;
292 349
293 BLOCK_INPUT; 350 BLOCK_INPUT;
294 351
297 code = alloca (sizeof (unsigned) * len); 354 code = alloca (sizeof (unsigned) * len);
298 for (i = 0; i < len; i++) 355 for (i = 0; i < len; i++)
299 code[i] = ((XCHAR2B_BYTE1 (s->char2b + from + i) << 8) 356 code[i] = ((XCHAR2B_BYTE1 (s->char2b + from + i) << 8)
300 | XCHAR2B_BYTE2 (s->char2b + from + i)); 357 | XCHAR2B_BYTE2 (s->char2b + from + i));
301 358
302 if (! face->extra) 359 gcs = face->extra;
303 { 360 if (gcs && face->gc != s->gc)
361 {
362 /* We are drawing for cursor or for mouse highlighting, and
363 can't use the prepared GCs. */
364 XGCValues xgcv;
365 unsigned long mask = GCForeground | GCBackground;
366
367 gcs = alloca (sizeof (GC) * 7);
368 XGetGCValues (FRAME_X_DISPLAY (f), s->gc, mask, &xgcv);
369 if (ftxfont_create_gcs (f, gcs, xgcv.foreground, xgcv.background) < 0)
370 gcs = NULL;
371 gcs[6] = s->gc;
372 }
373
374 if (! gcs)
375 {
376 /* We are drawing with a bitmap font which doesn't use
377 antialiasing. */
304 for (i = 0; i < len; i++) 378 for (i = 0; i < len; i++)
305 x += ftxfont_draw_bitmap (f, &face->gc, font, code[i], x, y, 379 x += ftxfont_draw_bitmap (f, &s->gc, font, code[i], x, y,
306 p, 0x700, n); 380 p, 0x700, n);
307 if (n[0] > 0) 381 if (n[0] > 0)
308 XDrawPoints (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f), 382 XDrawPoints (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f),
309 face->gc, p, n[0], CoordModeOrigin); 383 s->gc, p, n[0], CoordModeOrigin);
310 } 384 }
311 else 385 else
312 { 386 {
313 GC *gc = face->extra; 387 /* We are drawing with a scalable font which use
314 388 antialiasing. */
315 for (i = 0; i < len; i++) 389 for (i = 0; i < len; i++)
316 x += ftxfont_draw_bitmap (f, &face->gc, font, code[i], x, y, 390 x += ftxfont_draw_bitmap (f, gcs, font, code[i], x, y,
317 p, 0x100, n); 391 p, 0x100, n);
318 for (i = 0; i < 7; i++) 392 for (i = 0; i < 7; i++)
319 if (n[i] > 0) 393 if (n[i] > 0)
320 XDrawPoints (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f), 394 XDrawPoints (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f),
321 gc[i], p + 0x100 * i, n[i], CoordModeOrigin); 395 gcs[i], p + 0x100 * i, n[i], CoordModeOrigin);
396 if (face->gc != s->gc)
397 for (i = 0; i < 6; i++)
398 XFreeGC (FRAME_X_DISPLAY (f), gcs[i]);
322 } 399 }
323 400
324 UNBLOCK_INPUT; 401 UNBLOCK_INPUT;
325 402
326 return len; 403 return len;