merge FLT
[m17n/m17n-lib.git] / src / face.c
1 /* face.c -- face module.
2    Copyright (C) 2003, 2004
3      National Institute of Advanced Industrial Science and Technology (AIST)
4      Registration Number H15PRO112
5
6    This file is part of the m17n library.
7
8    The m17n library is free software; you can redistribute it and/or
9    modify it under the terms of the GNU Lesser General Public License
10    as published by the Free Software Foundation; either version 2.1 of
11    the License, or (at your option) any later version.
12
13    The m17n library is distributed in the hope that it will be useful,
14    but WITHOUT ANY WARRANTY; without even the implied warranty of
15    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16    Lesser General Public License for more details.
17
18    You should have received a copy of the GNU Lesser General Public
19    License along with the m17n library; if not, write to the Free
20    Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
21    02111-1307, USA.  */
22
23 /***en
24     @addtogroup m17nFace
25     @brief A face is an object to control appearance of M-text.
26
27     A @e face is an object of the type #MFace and controls how to
28     draw M-texts.  A face has a fixed number of @e face @e properties.
29     Like other types of properties, a face property consists of a key
30     and a value.  A key is one of the following symbols:
31
32     #Mforeground, #Mbackground, #Mvideomode, #Mhline, #Mbox,
33     #Mfoundry, #Mfamily, #Mweight, #Mstyle, #Mstretch, #Madstyle,
34     #Msize, #Mfontset, #Mratio, #Mhook_func, #Mhook_arg
35
36     "The face property that belongs to face F and whose key is @c xxx"
37     may be shortened to "the xxx property of F".
38
39     The M-text drawing functions first search an M-text for the text
40     property whose key is the symbol #Mface, then draw the M-text
41     using the value of that text property.  This value must be a
42     pointer to a face object.
43
44     If there are multiple text properties whose key is @c Mface, and
45     they are not conflicting one another, properties of those faces
46     are merged and used.
47
48     If no faces specify a certain property, the value of the default
49     face is used.  */
50
51 /***ja
52     @addtogroup m17nFace
53     @brief ¥Õ¥§¡¼¥¹¤È¤Ï¡¢M-text ¤Î¸«±É¤¨¤òÀ©¸æ¤¹¤ë¥ª¥Ö¥¸¥§¥¯¥È¤Ç¤¢¤ë.
54
55     @e ¥Õ¥§¡¼¥¹ ¤Ï #MFace ·¿¤Î¥ª¥Ö¥¸¥§¥¯¥È¤Ç¤¢¤ê¡¢M-text 
56     ¤Îɽ¼¨ÊýË¡¤òÀ©¸æ¤¹¤ë¡£¥Õ¥§¡¼¥¹¤Ï¸ÇÄê¸Ä¤Î @e ¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£ ¤ò»ý¤Ä¡£
57     Â¾¤Î¥×¥í¥Ñ¥Æ¥£Æ±ÍÍ¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¤Ï¥­¡¼¤ÈÃͤ«¤é¤Ê¤ê¡¢¥­¡¼¤Ï°Ê²¼¤Î¥·¥ó¥Ü¥ë¤Î¤¤¤º¤ì¤«¤Ç¤¢¤ë¡£
58
59     #Mforeground, #Mbackground, #Mvideomode, #Mhline, #Mbox, 
60     #Mfoundry, #Mfamily, #Mweight, #Mstyle, #Mstretch, #Madstyle, 
61     #Msize, #Mfontset, #Mratio, #Mhook_func, #Mhook_arg
62
63     ¡Ö¥Õ¥§¡¼¥¹ F ¤Î¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¤Î¤¦¤Á¥­¡¼¤¬ @c Mxxx 
64     ¤Ç¤¢¤ë¤â¤Î¡×¤Î¤³¤È¤ò´Êñ¤Ë¡ÖF ¤Î xxx ¥×¥í¥Ñ¥Æ¥£¡×¤È¸Æ¤Ö¤³¤È¤¬¤¢¤ë¡£
65
66     M-text ¤Îɽ¼¨´Ø¿ô¤Ï¡¢¤Þ¤ººÇ½é¤Ë¤½¤Î M-text ¤«¤é¥­¡¼¤¬¥·¥ó¥Ü¥ë 
67     #Mface ¤Ç¤¢¤ë¤è¤¦¤Ê¥Æ¥­¥¹¥È¥×¥í¥Ñ¥Æ¥£¤òõ¤·¡¢¼¡¤Ë¤½¤ÎÃͤ˽¾¤Ã¤Æ 
68     M-text ¤òɽ¼¨¤¹¤ë¡£¤³¤ÎÃͤϥե§¡¼¥¹¥ª¥Ö¥¸¥§¥¯¥È¤Ø¤Î¥Ý¥¤¥ó¥¿¤Ç¤Ê¤±¤ì¤Ð¤Ê¤é¤Ê¤¤¡£
69
70     M-text ¤¬¡¢#Mface 
71     ¤ò¥­¡¼¤È¤¹¤ë¥Æ¥­¥¹¥È¥×¥í¥Ñ¥Æ¥£¤òÊ£¿ô»ý¤Ã¤Æ¤ª¤ê¡¢¤«¤Ä¤½¤ì¤é¤ÎÃͤ¬¾×Æͤ·¤Ê¤¤¤Ê¤é¤Ð¡¢¥Õ¥§¡¼¥¹¾ðÊó¤ÏÁȤ߹ç¤ï¤µ¤ì¤ÆÍѤ¤¤é¤ì¤ë¡£
72
73     ¤¢¤ë¥Æ¥­¥¹¥È°À­¤¬¤É¤Î¥Õ¥§¡¼¥¹¤Ë¤è¤Ã¤Æ¤â»ØÄꤵ¤ì¤Æ¤¤¤Ê¤¤¾ì¹ç¤Ï¡¢¥Ç¥Õ¥©¥ë¥È¥Õ¥§¡¼¥¹¤ÎÃͤ¬ÍѤ¤¤é¤ì¤ë¡£  */
74
75 /*=*/
76
77 #if !defined (FOR_DOXYGEN) || defined (DOXYGEN_INTERNAL_MODULE)
78 /*** @addtogroup m17nInternal
79      @{ */
80
81 #include <stdio.h>
82 #include <stdlib.h>
83 #include <string.h>
84 #include <ctype.h>
85
86 #include "config.h"
87 #include "m17n-gui.h"
88 #include "m17n-misc.h"
89 #include "internal.h"
90 #include "charset.h"
91 #include "symbol.h"
92 #include "plist.h"
93 #include "mtext.h"
94 #include "textprop.h"
95 #include "internal-gui.h"
96 #include "face.h"
97 #include "font.h"
98 #include "fontset.h"
99
100 static M17NObjectArray face_table;
101
102 MSymbol Mlatin;
103
104 static MSymbol M_face_prop_index;
105
106 static MPlist *hline_prop_list;
107 static MPlist *box_prop_list;
108
109 /** Special hook function pointer that does nothing.  */
110 static MFaceHookFunc noop_hook;
111
112 /**  */
113 static MFaceHLineProp *
114 get_hline_create (MFaceHLineProp *prop)
115 {
116   MPlist *plist;
117   MFaceHLineProp *hline;
118
119   if (prop->width == 0)
120     return MPLIST_VAL (hline_prop_list);
121   MPLIST_DO (plist, MPLIST_NEXT (hline_prop_list))
122     {
123       hline = MPLIST_VAL (plist);
124       if (prop->type == hline->type
125           && prop->width == hline->width
126           && prop->color == hline->color)
127         return hline;
128     }
129   MSTRUCT_MALLOC (hline, MERROR_FACE);
130   *hline = *prop;
131   mplist_push (plist, Mt, hline);
132   return hline;
133 }
134
135 static MFaceBoxProp *
136 get_box_create (MFaceBoxProp *prop)
137 {
138   MPlist *plist;
139   MFaceBoxProp *box;
140
141   if (prop->width == 0)
142     return MPLIST_VAL (box_prop_list);
143   MPLIST_DO (plist, MPLIST_NEXT (box_prop_list))
144     {
145       box = MPLIST_VAL (plist);
146       if (prop->width == box->width
147           && prop->color_top == box->color_top
148           && prop->color_bottom == box->color_bottom
149           && prop->color_left == box->color_left
150           && prop->color_right == box->color_right
151           && prop->inner_hmargin == box->inner_hmargin
152           && prop->inner_vmargin == box->inner_vmargin
153           && prop->outer_hmargin == box->inner_hmargin
154           && prop->inner_vmargin == box->inner_vmargin)
155         return box;
156     }
157   MSTRUCT_MALLOC (box, MERROR_FACE);
158   *box = *prop;
159   mplist_push (plist, Mt, box);
160   return box;
161 }
162
163 /** From FRAME->realized_face_list, find a realized face based on
164     FACE.  */
165
166 static MRealizedFace *
167 find_realized_face (MFrame *frame, MFace *face, MFont *font)
168 {
169   MPlist *plist;
170
171   MPLIST_DO (plist, frame->realized_face_list)
172     {
173       MRealizedFace *rface = MPLIST_VAL (plist);
174
175       if (memcmp (rface->face.property, face->property,
176                   sizeof face->property) == 0
177           && (rface->font
178               ? (font && ! memcmp (rface->font, font, sizeof (MFont)))
179               : ! font))
180         return rface;
181     }
182   return NULL;
183 }
184
185 static void
186 free_face (void *object)
187 {
188   MFace *face = (MFace *) object;
189
190   if (face->property[MFACE_FONTSET])
191     M17N_OBJECT_UNREF (face->property[MFACE_FONTSET]);
192   M17N_OBJECT_UNREF (face->frame_list);
193   M17N_OBJECT_UNREGISTER (face_table, face);
194   free (object);
195 }
196
197
198 static MPlist *
199 serialize_hline (MPlist *plist, MFaceHLineProp *hline)
200 {
201   if (hline->width > 0)
202     {
203       MPlist *pl = mplist ();
204
205       mplist_add (pl, Minteger, (void *) hline->type);
206       mplist_add (pl, Minteger, (void *) hline->width);
207       mplist_add (pl, Msymbol, hline->color);
208       plist = mplist_add (plist, Mplist, pl);
209       M17N_OBJECT_UNREF (pl);
210     }
211   return plist;
212 }
213
214 static MPlist *
215 serialize_box (MPlist *plist, MFaceBoxProp *box)
216 {
217   if (box->width > 0)
218     {
219       MPlist *pl = mplist ();
220
221       mplist_add (pl, Minteger, (void *) box->width);
222       mplist_add (pl, Minteger, (void *) box->inner_hmargin);
223       mplist_add (pl, Minteger, (void *) box->inner_vmargin);
224       mplist_add (pl, Minteger, (void *) box->outer_hmargin);
225       mplist_add (pl, Minteger, (void *) box->outer_vmargin);
226       mplist_add (pl, Msymbol, box->color_top);
227       mplist_add (pl, Msymbol, box->color_bottom);
228       mplist_add (pl, Msymbol, box->color_left);
229       mplist_add (pl, Msymbol, box->color_right);
230       plist = mplist_add (plist, Mplist, pl);
231       M17N_OBJECT_UNREF (pl);
232     }
233   return plist;
234 }
235
236 static MPlist *
237 serialize_face (void *val)
238 {
239   MFace *face = val;
240   MPlist *plist = mplist (), *pl = plist;
241   int i;
242   struct {
243     MSymbol *key;
244     MSymbol *type;
245     MPlist *(*func) (MPlist *plist, void *val);
246   } serializer[MFACE_RATIO + 1]
247       = { { &Mfoundry,          &Msymbol },
248           { &Mfamily,           &Msymbol },
249           { &Mweight,           &Msymbol },
250           { &Mstyle,            &Msymbol },
251           { &Mstretch,          &Msymbol },
252           { &Madstyle,          &Msymbol },
253           { &Msize,             &Minteger },
254           { &Mfontset,          NULL },
255           { &Mforeground,       &Msymbol },
256           { &Mbackground,       &Msymbol },
257           { &Mhline,            NULL },
258           { &Mbox,              NULL },
259           { &Mvideomode,        &Msymbol },
260           { &Mratio,            &Minteger } };
261   
262   for (i = 0; i <= MFACE_RATIO; i++)
263     if (face->property[i] && serializer[i].key)
264       {
265         pl = mplist_add (pl, Msymbol, *serializer[i].key);
266         if (serializer[i].type)
267           pl = mplist_add (pl, *serializer[i].type, face->property[i]);
268         else if (i == MFACE_FONTSET)
269           pl = mplist_add (pl, Msymbol, mfontset_name ((MFontset *)
270                                                        face->property[i]));
271         else if (i == MFACE_HLINE)
272           pl = serialize_hline (pl, (MFaceHLineProp *) face->property[i]);
273         else if (i == MFACE_BOX)
274           pl = serialize_box (pl, (MFaceBoxProp *) face->property[i]);
275       }
276
277   return plist;
278 }
279
280 static void *
281 deserialize_hline (MPlist *plist)
282 {
283   MFaceHLineProp hline, *hline_ret;
284
285   if (! MPLIST_INTEGER_P (plist))
286     MERROR (MERROR_FACE, NULL);
287   hline.type = MPLIST_INTEGER_P (plist);
288   plist = MPLIST_NEXT (plist);
289   if (! MPLIST_INTEGER_P (plist))
290     MERROR (MERROR_FACE, NULL);
291   hline.width = MPLIST_INTEGER_P (plist);
292   plist = MPLIST_NEXT (plist);
293   if (! MPLIST_SYMBOL_P (plist))
294     MERROR (MERROR_FACE, NULL);
295   hline.color = MPLIST_SYMBOL (plist);
296   MSTRUCT_MALLOC (hline_ret, MERROR_FACE);
297   *hline_ret = hline;
298   return hline_ret;
299 }
300
301 static void *
302 deserialize_box (MPlist *plist)
303 {
304   MFaceBoxProp box, *box_ret;
305
306   if (! MPLIST_INTEGER_P (plist))
307     MERROR (MERROR_FACE, NULL);
308   box.width = MPLIST_INTEGER (plist);
309   plist = MPLIST_NEXT (plist);
310   if (! MPLIST_INTEGER_P (plist))
311     MERROR (MERROR_FACE, NULL);
312   box.inner_hmargin = MPLIST_INTEGER (plist);
313   plist = MPLIST_NEXT (plist);
314   if (! MPLIST_INTEGER_P (plist))
315     MERROR (MERROR_FACE, NULL);
316   box.inner_vmargin = MPLIST_INTEGER (plist);
317   plist = MPLIST_NEXT (plist);
318   if (! MPLIST_INTEGER_P (plist))
319     MERROR (MERROR_FACE, NULL);
320   box.outer_hmargin = MPLIST_INTEGER (plist);
321   plist = MPLIST_NEXT (plist);
322   if (! MPLIST_INTEGER_P (plist))
323     MERROR (MERROR_FACE, NULL);
324   box.outer_vmargin = MPLIST_INTEGER (plist);
325   plist = MPLIST_NEXT (plist);
326   if (! MPLIST_SYMBOL_P (plist))
327     MERROR (MERROR_FACE, NULL);
328   box.color_top = MPLIST_SYMBOL (plist);
329   plist = MPLIST_NEXT (plist);
330   if (! MPLIST_SYMBOL_P (plist))
331     MERROR (MERROR_FACE, NULL);
332   box.color_bottom = MPLIST_SYMBOL (plist);
333   plist = MPLIST_NEXT (plist);
334   if (! MPLIST_SYMBOL_P (plist))
335     MERROR (MERROR_FACE, NULL);
336   box.color_left = MPLIST_SYMBOL (plist);
337   plist = MPLIST_NEXT (plist);
338   if (! MPLIST_SYMBOL_P (plist))
339     MERROR (MERROR_FACE, NULL);
340   box.color_right = MPLIST_SYMBOL (plist);
341   MSTRUCT_MALLOC (box_ret, MERROR_FACE);
342   *box_ret = box;
343   return box_ret;
344 }
345
346 static void *
347 deserialize_face (MPlist *plist)
348 {
349   MFace *face = mface ();
350
351   MPLIST_DO (plist, plist)
352     {
353       MSymbol key;
354       int index;
355       void *val;
356
357       if (! MPLIST_SYMBOL_P (plist))
358         break;
359       key = MPLIST_SYMBOL (plist);
360       index = (int) msymbol_get (key, M_face_prop_index) - 1;
361       plist = MPLIST_NEXT (plist);
362       if (MPLIST_TAIL_P (plist))
363         break;
364       if (index < 0 || index > MFACE_RATIO)
365         continue;
366       if (key == Mfoundry || key == Mfamily || key == Mweight || key == Mstyle
367           || key == Mstretch || key == Madstyle
368           || key == Mforeground || key == Mbackground || key == Mvideomode)
369         {
370           if (! MPLIST_SYMBOL_P (plist))
371             continue;
372           val = MPLIST_VAL (plist);
373         }
374       else if (key == Msize || key == Mratio)
375         {
376           if (! MPLIST_INTEGER_P (plist))
377             continue;
378           val = MPLIST_VAL (plist);
379         }
380       else if (key == Mfontset)
381         {
382           if (! MPLIST_SYMBOL_P (plist))
383             continue;
384           val = mfontset (MSYMBOL_NAME (MPLIST_SYMBOL (plist)));
385         }
386       else if (key == Mhline)
387         {
388           if (! MPLIST_PLIST_P (plist))
389             continue;
390           val = deserialize_hline (MPLIST_PLIST (plist));
391         }
392       else if (key == Mbox)
393         {
394           if (! MPLIST_PLIST_P (plist))
395             continue;
396           val = deserialize_box (MPLIST_PLIST (plist));
397         }
398       face->property[index] = val;
399     }
400   return face;
401 }
402
403 static MGlyphString work_gstring;
404
405 \f
406
407 /* Internal API */
408
409 MFace *mface__default;
410
411 int
412 mface__init ()
413 {
414   int i;
415   MFaceHLineProp *hline;
416   MFaceBoxProp *box;
417
418   M17N_OBJECT_ADD_ARRAY (face_table, "Face");
419   Mface = msymbol_as_managing_key ("face");
420   msymbol_put_func (Mface, Mtext_prop_serializer,
421                     M17N_FUNC (serialize_face));
422   msymbol_put_func (Mface, Mtext_prop_deserializer,
423                     M17N_FUNC (deserialize_face));
424
425   Mforeground = msymbol ("foreground");
426   Mbackground = msymbol ("background");
427   Mvideomode = msymbol ("videomode");
428   Mnormal = msymbol ("normal");
429   Mreverse = msymbol ("reverse");
430   Mratio = msymbol ("ratio");
431   Mhline = msymbol ("hline");
432   Mbox = msymbol ("box");
433   Mhook_func = msymbol ("hook-func");
434   Mhook_arg = msymbol ("hook-arg");
435
436   Mlatin = msymbol ("latin");
437   M_face_prop_index = msymbol ("  face-prop-index");
438
439   {
440     struct {
441       /* Pointer to the key symbol of the face property.  */
442       MSymbol *key;
443       /* Index (enum face_property) of the face property. */
444       int index;
445     } mface_prop_data[MFACE_HOOK_ARG + 1] =
446         { { &Mfoundry,          MFACE_FOUNDRY },
447           { &Mfamily,           MFACE_FAMILY },
448           { &Mweight,           MFACE_WEIGHT },
449           { &Mstyle,            MFACE_STYLE },
450           { &Mstretch,          MFACE_STRETCH },
451           { &Madstyle,          MFACE_ADSTYLE },
452           { &Msize,             MFACE_SIZE },
453           { &Mfontset,          MFACE_FONTSET },
454           { &Mforeground,       MFACE_FOREGROUND },
455           { &Mbackground,       MFACE_BACKGROUND },
456           { &Mhline,            MFACE_HLINE },
457           { &Mbox,              MFACE_BOX },
458           { &Mvideomode,        MFACE_VIDEOMODE },
459           { &Mratio,            MFACE_RATIO },
460           { &Mhook_arg,         MFACE_HOOK_ARG } };
461
462     for (i = 0; i < MFACE_PROPERTY_MAX; i++)
463       /* We add one to distinguish it from no-property.  */
464       msymbol_put (*mface_prop_data[i].key, M_face_prop_index,
465                    (void *) (mface_prop_data[i].index + 1));
466   }
467
468   hline_prop_list = mplist ();
469   MSTRUCT_CALLOC (hline, MERROR_FACE);
470   mplist_push (hline_prop_list, Mt, hline);
471   box_prop_list = mplist ();
472   MSTRUCT_CALLOC (box, MERROR_FACE);
473   mplist_push (box_prop_list, Mt, box);
474
475   mface__default = mface ();
476   mface__default->property[MFACE_FOUNDRY] = msymbol ("misc");
477   mface__default->property[MFACE_FAMILY] = msymbol ("fixed");
478   mface__default->property[MFACE_WEIGHT] = msymbol ("medium");
479   mface__default->property[MFACE_STYLE] = msymbol ("r");
480   mface__default->property[MFACE_STRETCH] = msymbol ("normal");
481   mface__default->property[MFACE_ADSTYLE] = msymbol ("");
482   mface__default->property[MFACE_SIZE] = (void *) 120;
483   mface__default->property[MFACE_FONTSET] = mfontset (NULL);
484   mface__default->property[MFACE_FOREGROUND] = msymbol ("black");
485   mface__default->property[MFACE_BACKGROUND] = msymbol ("white");
486   mface__default->property[MFACE_HLINE] = hline;
487   mface__default->property[MFACE_BOX] = box;
488   mface__default->property[MFACE_VIDEOMODE] = Mnormal;
489   mface__default->hook = noop_hook;
490
491   mface_normal_video = mface ();
492   mface_normal_video->property[MFACE_VIDEOMODE] = (void *) Mnormal;
493
494   mface_reverse_video = mface ();
495   mface_reverse_video->property[MFACE_VIDEOMODE] = (void *) Mreverse;
496
497   {
498     MFaceHLineProp hline_prop;
499
500     hline_prop.type = MFACE_HLINE_UNDER;
501     hline_prop.width = 1;
502     hline_prop.color = Mnil;
503     mface_underline = mface ();
504     mface_put_prop (mface_underline, Mhline, &hline_prop);
505   }
506
507   mface_medium = mface ();
508   mface_medium->property[MFACE_WEIGHT] = (void *) msymbol ("medium");
509   mface_bold = mface ();
510   mface_bold->property[MFACE_WEIGHT] = (void *) msymbol ("bold");
511   mface_italic = mface ();
512   mface_italic->property[MFACE_STYLE] = (void *) msymbol ("i");
513   mface_bold_italic = mface_copy (mface_bold);
514   mface_bold_italic->property[MFACE_STYLE]
515     = mface_italic->property[MFACE_STYLE];
516
517   mface_xx_small = mface ();
518   mface_xx_small->property[MFACE_RATIO] = (void *) 50;
519   mface_x_small = mface ();
520   mface_x_small->property[MFACE_RATIO] = (void *) 67;
521   mface_small = mface ();
522   mface_small->property[MFACE_RATIO] = (void *) 75;
523   mface_normalsize = mface ();
524   mface_normalsize->property[MFACE_RATIO] = (void *) 100;
525   mface_large = mface ();
526   mface_large->property[MFACE_RATIO] = (void *) 120;
527   mface_x_large = mface ();
528   mface_x_large->property[MFACE_RATIO] = (void *) 150;
529   mface_xx_large = mface ();
530   mface_xx_large->property[MFACE_RATIO] = (void *) 200;
531
532   mface_black = mface ();
533   mface_black->property[MFACE_FOREGROUND] = (void *) msymbol ("black");
534   mface_white = mface ();
535   mface_white->property[MFACE_FOREGROUND] = (void *) msymbol ("white");
536   mface_red = mface ();
537   mface_red->property[MFACE_FOREGROUND] = (void *) msymbol ("red");
538   mface_green = mface ();
539   mface_green->property[MFACE_FOREGROUND] = (void *) msymbol ("green");
540   mface_blue = mface ();
541   mface_blue->property[MFACE_FOREGROUND] = (void *) msymbol ("blue");
542   mface_cyan = mface ();
543   mface_cyan->property[MFACE_FOREGROUND] = (void *) msymbol ("cyan");
544   mface_yellow = mface ();
545   mface_yellow->property[MFACE_FOREGROUND] = (void *) msymbol ("yellow");
546   mface_magenta = mface ();
547   mface_magenta->property[MFACE_FOREGROUND] = (void *) msymbol ("magenta");
548
549   work_gstring.glyphs = malloc (sizeof (MGlyph) * 2);
550   work_gstring.size = 2;
551   work_gstring.used = 0;
552   work_gstring.inc = 1;
553   return 0;
554 }
555
556 void
557 mface__fini ()
558 {
559   MPlist *plist;
560
561   M17N_OBJECT_UNREF (mface__default);
562   M17N_OBJECT_UNREF (mface_normal_video);
563   M17N_OBJECT_UNREF (mface_reverse_video);
564   M17N_OBJECT_UNREF (mface_underline);
565   M17N_OBJECT_UNREF (mface_medium);
566   M17N_OBJECT_UNREF (mface_bold);
567   M17N_OBJECT_UNREF (mface_italic);
568   M17N_OBJECT_UNREF (mface_bold_italic);
569   M17N_OBJECT_UNREF (mface_xx_small);
570   M17N_OBJECT_UNREF (mface_x_small);
571   M17N_OBJECT_UNREF (mface_small);
572   M17N_OBJECT_UNREF (mface_normalsize);
573   M17N_OBJECT_UNREF (mface_large);
574   M17N_OBJECT_UNREF (mface_x_large);
575   M17N_OBJECT_UNREF (mface_xx_large);
576   M17N_OBJECT_UNREF (mface_black);
577   M17N_OBJECT_UNREF (mface_white);
578   M17N_OBJECT_UNREF (mface_red);
579   M17N_OBJECT_UNREF (mface_green);
580   M17N_OBJECT_UNREF (mface_blue);
581   M17N_OBJECT_UNREF (mface_cyan);
582   M17N_OBJECT_UNREF (mface_yellow);
583   M17N_OBJECT_UNREF (mface_magenta);
584
585   MPLIST_DO (plist, hline_prop_list)
586     free (MPLIST_VAL (plist));
587   M17N_OBJECT_UNREF (hline_prop_list);
588   MPLIST_DO (plist, box_prop_list)
589     free (MPLIST_VAL (plist));
590   M17N_OBJECT_UNREF (box_prop_list);
591
592   free (work_gstring.glyphs);
593 }
594
595 /** Return a face realized from NUM number of base faces pointed by
596     FACES on the frame FRAME.  If SIZE is nonzero, it specifies the
597     maximum font size.  */
598
599 MRealizedFace *
600 mface__realize (MFrame *frame, MFace **faces, int num, int size, MFont *font)
601 {
602   MRealizedFace *rface;
603   MRealizedFont *rfont;
604   MFace merged_face = *(frame->face);
605   int i, j;
606   MFaceHookFunc func;
607   MFont spec;
608
609   if (num == 0 && frame->rface && ! font)
610     return frame->rface;
611
612   if (! mplist_find_by_value (frame->face->frame_list, frame))
613     mplist_push (frame->face->frame_list, Mt, frame);
614   for (i = 0; i < num; i++)
615     if (! mplist_find_by_value (faces[i]->frame_list, frame))
616       mplist_push (faces[i]->frame_list, Mt, frame);
617
618   for (i = 0; i < MFACE_PROPERTY_MAX; i++)
619     for (j = num - 1; j >= 0; j--)
620       if (faces[j]->property[i])
621         {
622           merged_face.property[i] = faces[j]->property[i];
623           break;
624         }
625
626   if (font)
627     {
628       if (font->type != MFONT_TYPE_REALIZED)
629         font = mfont_copy (font);
630       for (i = 0; i <= MFACE_ADSTYLE; i++)
631         if (font->property[i])
632           merged_face.property[i] = FONT_PROPERTY (font, i);
633       if (font->size)
634         {
635           int font_size;
636
637           if (font->size < 0)
638             font->size = ((double) (- font->size)) * frame->dpi / 72.27 + 0.5;
639           font_size = font->size;
640           merged_face.property[MFACE_SIZE] = (void *) font_size;
641           merged_face.property[MFACE_RATIO] = (void *) 0;
642         }
643     }
644
645   if (! font || ! font->size)
646     {
647       double font_size = (int) merged_face.property[MFACE_SIZE];
648       int ifont_size;
649
650       if (font_size < 0)
651         font_size = - font_size * frame->dpi / 72.27;
652       if (merged_face.property[MFACE_RATIO]
653           && (int) merged_face.property[MFACE_RATIO] != 100)
654         {
655           font_size *= (int) merged_face.property[MFACE_RATIO];
656           font_size /= 100;
657         }
658       ifont_size = font_size + 0.5;
659       merged_face.property[MFACE_SIZE] = (void *) ifont_size;
660       merged_face.property[MFACE_RATIO] = (void *) 0;
661     }
662
663   merged_face.property[MFACE_FOUNDRY] = Mnil;
664   rface = find_realized_face (frame, &merged_face, font);
665   if (rface)
666     {
667       if (font && font->type != MFONT_TYPE_REALIZED)
668         free (font);
669       return rface;
670     }
671
672   MSTRUCT_CALLOC (rface, MERROR_FACE);
673   mplist_push (frame->realized_face_list, Mt, rface);
674   rface->frame = frame;
675   rface->face = merged_face;
676   rface->font = font;
677
678   if (font)
679     {
680       if (font->type == MFONT_TYPE_SPEC)
681         rfont = (MRealizedFont *) mfont_find (frame, font, NULL, 0);
682       else if (font->type == MFONT_TYPE_OBJECT)
683         {
684           MFONT_INIT (&spec);
685           spec.size = (int) merged_face.property[MFONT_SIZE];
686           if (font->property[MFONT_REGISTRY])
687             spec.property[MFONT_REGISTRY] = font->property[MFONT_REGISTRY];
688           else
689             mfont_put_prop (&spec, Mregistry,
690                             (font->source == MFONT_SOURCE_X
691                              ? Miso8859_1 : Municode_bmp));
692           rfont = mfont__open (frame, font, &spec);
693         }
694       else
695         rfont = (MRealizedFont *) font;
696     }
697   else
698     {
699       MFontset *fontset = (MFontset *) merged_face.property[MFACE_FONTSET];
700
701       rface->rfontset = mfont__realize_fontset (frame, fontset, &merged_face,
702                                                 font);
703       rfont = NULL;
704       mfont__set_spec_from_face (&spec, &merged_face);
705       mfont_put_prop (&spec, Mregistry, Municode_bmp);
706       spec.source = MFONT_SOURCE_FT;
707       font = mfont__select (frame, &spec, 0);
708       if (font)
709         rfont = mfont__open (frame, font, &spec);
710       if (! rfont)
711         {
712           mfont_put_prop (&spec, Mregistry, Miso8859_1);
713           spec.source = MFONT_SOURCE_X;
714           font = mfont__select (frame, &spec, 0);
715           if (font)
716             rfont = mfont__open (frame, font, &spec);
717         }
718       if (! rfont)
719         {
720           num = 0;
721           rfont = mfont__lookup_fontset (rface->rfontset, NULL, &num,
722                                          Mlatin, Mnil, Mnil, size, 0);
723         }
724     }
725
726   if (rfont)
727     {
728       rface->rfont = rfont;
729       rface->layouter = rfont->layouter;
730       rfont->layouter = Mnil;
731       work_gstring.glyphs[0].rface = rface;
732       work_gstring.glyphs[0].g.code = MCHAR_INVALID_CODE;
733       work_gstring.glyphs[0].g.measured = 0;
734       mfont__get_metric (&work_gstring, 0, 1);
735       rface->ascent = work_gstring.glyphs[0].g.ascent;
736       rface->descent = work_gstring.glyphs[0].g.descent;
737       work_gstring.glyphs[0].g.code
738         = mfont__encode_char (frame, (MFont *) rfont, NULL, ' ');
739       if (work_gstring.glyphs[0].g.code != MCHAR_INVALID_CODE)
740         {
741           work_gstring.glyphs[0].g.measured = 0;
742           mfont__get_metric (&work_gstring, 0, 1);
743           rface->space_width = work_gstring.glyphs[0].g.xadv;
744         }
745       else
746         rface->space_width = rfont->spec.size / 10;
747       if (rfont->average_width)
748         rface->average_width = rfont->average_width >> 6;
749       else
750         {
751           work_gstring.glyphs[0].g.code
752             = mfont__encode_char (frame, (MFont *) rfont, NULL, 'x');
753           if (work_gstring.glyphs[0].g.code != MCHAR_INVALID_CODE)
754             {
755               work_gstring.glyphs[0].g.measured = 0;
756               mfont__get_metric (&work_gstring, 0, 1);
757               rface->average_width = work_gstring.glyphs[0].g.xadv;
758             }
759           else
760             rface->average_width = rface->space_width;
761         }
762     }
763   else
764     {
765       rface->rfont = NULL;
766       rface->space_width = frame->space_width;
767     }
768
769   rface->hline = (MFaceHLineProp *) merged_face.property[MFACE_HLINE];
770   if (rface->hline && rface->hline->width == 0)
771     rface->hline = NULL;
772   rface->box = (MFaceBoxProp *) merged_face.property[MFACE_BOX];
773   if (rface->box && rface->box->width == 0)
774     rface->box = NULL;
775   rface->ascii_rface = rface;
776   (*frame->driver->realize_face) (rface);
777
778   func = rface->face.hook;
779   if (func && func != noop_hook)
780     (func) (&(rface->face), rface->info, rface->face.property[MFACE_HOOK_ARG]);
781
782   rface->non_ascii_list = mplist ();
783   if (rface->rfont)
784     {
785       MRealizedFace *nofont;
786
787       MSTRUCT_CALLOC (nofont, MERROR_FACE);
788       *nofont = *rface;
789       nofont->non_ascii_list = NULL;
790       nofont->rfont = NULL;
791       mplist_add (rface->non_ascii_list, Mt, nofont);
792     }
793
794   return rface;
795 }
796
797
798 MGlyph *
799 mface__for_chars (MSymbol script, MSymbol language, MSymbol charset,
800                   MGlyph *from_g, MGlyph *to_g, int size)
801 {
802   MRealizedFont *rfont = from_g->rface->rfont;
803   MSymbol layouter;
804   int num = to_g - from_g;
805   int i;
806
807   if (from_g->rface->font)
808     {
809       MRealizedFace *rface = from_g->rface, *new;
810
811       if (! rfont)
812         rfont = mfontset__get_font (rface->frame,
813                                     rface->face.property[MFACE_FONTSET], 
814                                     script, language,
815                                     rface->font, NULL);
816       else if (script != Mlatin)
817         rfont = mfontset__get_font (rface->frame,
818                                     rface->face.property[MFACE_FONTSET],
819                                     script, language,
820                                     (MFont *) rfont, NULL);
821       if (! rfont)
822         {
823           for (; from_g < to_g && from_g->rface->font; from_g++)
824             from_g->g.code = MCHAR_INVALID_CODE;
825         }
826       else
827         {
828           if (rface->rfont == rfont && rfont->layouter == Mnil)
829             new = rface;
830           else
831             {
832               MSTRUCT_MALLOC (new, MERROR_FACE);
833               mplist_push (rface->non_ascii_list, Mt, new);
834               *new = *rface;
835               new->rfont = rfont;
836               new->layouter = rfont->layouter;
837               rfont->layouter = Mnil;
838               new->non_ascii_list = NULL;
839               new->ascent = rfont->ascent >> 6;
840               new->descent = rfont->descent >> 6;
841             } 
842           for (; from_g < to_g && from_g->rface->font; from_g++)
843             {
844               from_g->rface = new;
845               if (new->layouter)
846                 {
847                   MFLT *flt = mflt_get (new->layouter);
848                   MCharTable *coverage;
849
850                   if (! flt
851                       || ((coverage = mflt_coverage (flt))
852                           && ! (from_g->g.code
853                                 = (unsigned) mchartable_lookup (coverage,
854                                                                 from_g->g.c))))
855                     {
856                       from_g->rface = rface;
857                       from_g->g.code = mfont__encode_char (rfont->frame, 
858                                                            (MFont *) rfont,
859                                                            NULL, from_g->g.c);
860                     }
861                 }
862               else
863                 from_g->g.code = mfont__encode_char (rfont->frame, 
864                                                      (MFont *) rfont,
865                                                      NULL, from_g->g.c);
866             }
867         }
868       return from_g;
869     }
870
871   if (rfont && script == Mlatin)
872     {
873       for (i = 0; i < num; i++)
874         {
875           unsigned code = mfont__encode_char (rfont->frame, (MFont *) rfont,
876                                               NULL, from_g[i].g.c);
877           if (code == MCHAR_INVALID_CODE)
878             break;
879           from_g[i].g.code = code;
880         }
881       if (i == num || from_g[i].rface->font)
882         return from_g + i;
883     }
884
885   rfont = mfont__lookup_fontset (from_g->rface->rfontset, from_g, &num,
886                                  script, language, charset, size, 0);
887   if (rfont)
888     {
889       layouter = rfont->layouter;
890       rfont->layouter = Mnil;
891     }
892   else
893     {
894       from_g->g.code = MCHAR_INVALID_CODE;
895       num = 1;
896       rfont = NULL;
897       layouter = Mnil;
898     }
899   
900   to_g = from_g + num;
901   while (from_g < to_g)
902     {
903       MGlyph *g = from_g;
904       MRealizedFace *rface = from_g++->rface;
905
906       while (from_g < to_g && rface == from_g->rface) from_g++;
907       if (rface->rfont != rfont
908           || rface->layouter != layouter)
909         {
910           MPlist *plist = mplist_find_by_value (rface->non_ascii_list, rfont);
911           MRealizedFace *new = NULL;
912
913           while (plist)
914             {
915               new = MPLIST_VAL (plist);
916               if (new->layouter == layouter)
917                 break;
918               plist = mplist_find_by_value (MPLIST_NEXT (plist), rfont);
919             }
920           if (! plist)
921             {
922               MSTRUCT_MALLOC (new, MERROR_FACE);
923               mplist_push (rface->non_ascii_list, Mt, new);
924               *new = *rface;
925               new->rfont = rfont;
926               new->layouter = layouter;
927               new->non_ascii_list = NULL;
928               if (rfont)
929                 {
930                   new->ascent = rfont->ascent >> 6;
931                   new->descent = rfont->descent >> 6;
932                 }
933             }
934           while (g < from_g)
935             g++->rface = new;
936         }
937     }
938   return to_g;
939 }
940
941
942 void
943 mface__free_realized (MRealizedFace *rface)
944 {
945   MPlist *plist;
946
947   MPLIST_DO (plist, rface->non_ascii_list)
948     free (MPLIST_VAL (plist));
949   M17N_OBJECT_UNREF (rface->non_ascii_list);
950   if (rface->font && rface->font->type != MFONT_TYPE_REALIZED)
951     free (rface->font);
952   free (rface);
953 }
954
955 void
956 mface__update_frame_face (MFrame *frame)
957 {
958   frame->rface = NULL;
959   frame->rface = mface__realize (frame, NULL, 0, 0, NULL);
960   frame->space_width = frame->rface->space_width;
961   frame->average_width = frame->rface->average_width;
962   frame->ascent = frame->rface->ascent;
963   frame->descent = frame->rface->descent;
964 }
965
966 /*** @} */
967 #endif /* !FOR_DOXYGEN || DOXYGEN_INTERNAL_MODULE */
968
969 \f
970 /* External API  */
971 /*** @addtogroup m17nFace */
972 /*** @{ */
973 /*=*/
974
975 /***en @name Variables: Keys of face property */
976 /***ja @name ÊÑ¿ô: ¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¤Î¥­¡¼  */
977 /*** @{ */
978 /*=*/
979
980 /***en
981     @brief Key of a face property specifying foreground color.
982
983     The variable #Mforeground is used as a key of face property.  The
984     property value must be a symbol whose name is a color name, or
985     #Mnil.
986
987     #Mnil means that the face does not specify a foreground color.
988     Otherwise, the foreground of an M-text is drawn by the specified
989     color.  */
990 /***ja
991     @brief Á°·Ê¿§¤ò»ØÄꤹ¤ë¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¡¼¤Î¥­¡¼.
992
993     ÊÑ¿ô #Mforeground ¤Ï¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¤Î¥­¡¼¤È¤·¤ÆÍѤ¤¤é¤ì¤ë¡£
994     ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤϡ¢¿§Ì¾¤ò̾Á°¤È¤·¤Æ»ý¤Ä¥·¥ó¥Ü¥ë¤« #Mnil ¤Ç¤¢¤ë¡£
995
996     #Mnil ¤Î¾ì¹ç¡¢Á°·Ê¿§¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£¤½¤¦¤Ç¤Ê¤±¤ì¤Ð M-text 
997     ¤ÎÁ°·Ê¤Ï»ØÄꤵ¤ì¤¿¿§¤Çɽ¼¨¤µ¤ì¤ë¡£  */
998
999 MSymbol Mforeground;
1000
1001 /***en
1002     @brief Key of a face property specifying background color.
1003
1004     The variable #Mbackground is used as a key of face property.  The
1005     property value must be a symbol whose name is a color name, or
1006     #Mnil.
1007
1008     #Mnil means that the face does not specify a background color.
1009     Otherwise, the background of an M-text is drawn by the specified
1010     color.  */
1011 /***ja
1012     @brief ÇØ·Ê¿§¤ò»ØÄꤹ¤ë¤¿¤á¤Î¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¡¼¤Î¥­¡¼.
1013
1014     ÊÑ¿ô #Mbackground ¤Ï¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¤Î¥­¡¼¤È¤·¤ÆÍѤ¤¤é¤ì¤ë¡£
1015     ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤϡ¢¿§Ì¾¤ò̾Á°¤È¤·¤Æ»ý¤Ä¥·¥ó¥Ü¥ë¤« #Mnil ¤Ç¤¢¤ë¡£
1016
1017     #Mnil ¤Î¾ì¹ç¡¢ÇØ·Ê¿§¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£¤½¤¦¤Ç¤Ê¤±¤ì¤Ð M-text 
1018     ¤ÎÇطʤϻØÄꤵ¤ì¤¿¿§¤Çɽ¼¨¤µ¤ì¤ë¡£  */
1019
1020 MSymbol Mbackground;
1021
1022 /***en
1023     @brief Key of a face property specifying video mode.
1024
1025     The variable #Mvideomode is used as a key of face property.  The
1026     property value must be #Mnormal, #Mreverse, or #Mnil.
1027
1028     #Mnormal means that an M-text is drawn in normal video mode
1029     (i.e. the foreground is drawn by foreground color, the background
1030     is drawn by background color).
1031
1032     #Mreverse means that an M-text is drawn in reverse video mode
1033     (i.e. the foreground is drawn by background color, the background
1034     is drawn by foreground color).
1035
1036     #Mnil means that the face does not specify a video mode.  */
1037 /***ja
1038     @brief ¥Ó¥Ç¥ª¥â¡¼¥É¤ò»ØÄꤹ¤ë¤¿¤á¤Î¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¡¼¤Î¥­¡¼.
1039
1040     ÊÑ¿ô #Mvideomode ¤Ï¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¤Î¥­¡¼¤È¤·¤ÆÍѤ¤¤é¤ì¤ë¡£¥×¥í¥Ñ¥Æ¥£¤ÎÃͤϡ¢
1041     #Mnormal, #Mreverse, #Mnil ¤Î¤¤¤º¤ì¤«¤Ç¤Ê¤¯¤Æ¤Ï¤Ê¤é¤Ê¤¤¡£
1042
1043     #Mnormal ¤Î¾ì¹ç¤Ï¡¢M-text 
1044     ¤òɸ½à¤Î¥Ó¥Ç¥ª¥â¡¼¥É¡ÊÁ°·Ê¤òÁ°·Ê¿§¤Ç¡¢ÇطʤòÇØ·Ê¿§¤Ç¡Ë¤Çɽ¼¨¤¹¤ë¡£
1045
1046     #Mreverse ¤Î¾ì¹ç¤Ï¥ê¥Ð¡¼¥¹¥Ó¥Ç¥ª¥â¡¼¥É¤Ç¡ÊÁ°·Ê¤òÇØ·Ê¿§¤Ç¡¢ÇطʤòÁ°·Ê¿§¤Ç¡Ëɽ¼¨¤¹¤ë¡£
1047
1048     #Mnil ¤Î¾ì¹ç¤Ï¥Ó¥Ç¥ª¥â¡¼¥É¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£
1049     */
1050
1051 MSymbol Mvideomode;
1052
1053 /***en
1054     @brief Key of a face property specifying font size ratio.
1055
1056     The variable #Mratio is used as a key of face property.  The value
1057     RATIO must be an integer.
1058
1059     The value 0 means that the face does not specify a font size
1060     ratio.  Otherwise, an M-text is drawn by a font of size (FONTSIZE
1061     * RATIO / 100) where FONTSIZE is a font size specified by the face
1062     property #Msize.  */
1063 /***ja
1064     @brief ¥Õ¥©¥ó¥È¤Î¥µ¥¤¥º¤ÎÈæΨ¤ò»ØÄꤹ¤ë¤¿¤á¤Î¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¡¼¤Î¥­¡¼.
1065
1066     ÊÑ¿ô #Mratio ¤Ï¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¤Î¥­¡¼¤È¤·¤ÆÍѤ¤¤é¤ì¤ë¡£ÃÍ RATIO 
1067     ¤ÏÀ°¿ôÃͤǤʤ¯¤Æ¤Ï¤Ê¤é¤Ê¤¤¡£
1068
1069     Ãͤ¬0¤Ê¤é¤Ð¡¢¥Õ¥©¥ó¥È¥µ¥¤¥º¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£¤½¤¦¤Ç¤Ê¤±¤ì¤Ð¡¢M-text 
1070     ¤Ï(FONTSIZE * RATIO / 100) ¤È¤¤¤¦¥µ¥¤¥º¤Î¥Õ¥©¥ó¥È¤Çɽ¼¨¤µ¤ì¤ë¡£
1071     FONTSIZE ¤Ï¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¡¼#Msize ¤Ç»ØÄꤵ¤ì¤¿¥µ¥¤¥º¤Ç¤¢¤ë¡£ */
1072
1073 MSymbol Mratio;
1074
1075 /***en
1076     @brief Key of a face property specifying horizontal line.
1077
1078     The variable #Mhline is used as a key of face property.  The value
1079     must be a pointer to an object of type #MFaceHLineProp, or @c
1080     NULL.
1081
1082     The value @c NULL means that the face does not specify this
1083     property.  Otherwise, an M-text is drawn with a horizontal line by
1084     a way specified by the object that the value points to.  */
1085 /***ja
1086     @brief ¿åÊ¿Àþ¤ò»ØÄꤹ¤ë¤¿¤á¤Î¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¡¼¤Î¥­¡¼.
1087
1088     ÊÑ¿ô #Mhline ¤Ï¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¤Î¥­¡¼¤È¤·¤ÆÍѤ¤¤é¤ì¤ë¡£ÃͤϠ
1089     #MFaceHLineProp ·¿¥ª¥Ö¥¸¥§¥¯¥È¤Ø¤Î¥Ý¥¤¥ó¥¿¤« @c NULL ¤Ç¤Ê¤¯¤Æ¤Ï¤Ê¤é¤Ê¤¤¡£
1090
1091     Ãͤ¬ @c NULL ¤Ê¤é¤Ð¡¢¤³¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£
1092     ¤½¤¦¤Ç¤Ê¤±¤ì¤ÐÃͤ¬»Ø¤¹¥ª¥Ö¥¸¥§¥¯¥È¤Ë»ØÄꤵ¤ì¤¿¤è¤¦¤Ë¿åÊ¿Àþ¤òÉղ䷤ƠM-text 
1093     ¤òɽ¼¨¤¹¤ë¡£*/
1094
1095 MSymbol Mhline;
1096
1097 /***en
1098     @brief Key of a face property specifying box.
1099
1100     The variable #Mbox is used as a key of face property.  The value
1101     must be a pointer to an object of type #MFaceBoxProp, or @c NULL.
1102
1103     The value @c NULL means that the face does not specify a box.
1104     Otherwise, an M-text is drawn with a surrounding box by a way
1105     specified by the object that the value points to.  */
1106 /***ja
1107     @brief °Ï¤ßÏȤò»ØÄꤹ¤ë¤¿¤á¤Î¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¡¼¤Î¥­¡¼.
1108
1109     ÊÑ¿ô #Mbox ¤Ï¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¤Î¥­¡¼¤È¤·¤ÆÍѤ¤¤é¤ì¤ë¡£ÃͤϠ
1110     #MFaceBoxProp ·¿¥ª¥Ö¥¸¥§¥¯¥È¤Ø¤Î¥Ý¥¤¥ó¥¿¤« @c NULL ¤Ç¤Ê¤¯¤Æ¤Ï¤Ê¤é¤Ê¤¤¡£
1111
1112     Ãͤ¬ @c NULL ¤Ê¤é¤Ð¡¢¤³¤Î¥Õ¥§¡¼¥¹¤Ï°Ï¤ßÏȤò»ØÄꤷ¤Æ¤¤¤Ê¤¤¡£
1113     ¤½¤¦¤Ç¤Ê¤±¤ì¤ÐÃͤ¬»Ø¤¹¥ª¥Ö¥¸¥§¥¯¥È¤Ë»ØÄꤵ¤ì¤¿¤è¤¦¤Ë°Ï¤ßÏȤòÉղ䷤Ơ
1114     M-text ¤òɽ¼¨¤¹¤ë¡£*/
1115
1116 MSymbol Mbox;
1117
1118 /***en
1119     @brief Key of a face property specifying fontset.
1120
1121     The variable #Mfontset is used as a key of face property.  The
1122     value must be a pointer to an object of type #Mfontset, or @c
1123     NULL.
1124
1125     The value @c NULL means that the face does not specify a fontset.
1126     Otherwise, an M-text is drawn with a font selected from what
1127     specified in the fontset.  */
1128 /***ja
1129     @brief ¥Õ¥©¥ó¥È¥»¥Ã¥È¤ò»ØÄꤹ¤ë¤¿¤á¤Î¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¡¼¤Î¥­¡¼.
1130
1131     ÊÑ¿ô #Mfontset ¤Ï¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¤Î¥­¡¼¤È¤·¤ÆÍѤ¤¤é¤ì¤ë¡£ÃͤϠ
1132     #Mfontset ·¿¥ª¥Ö¥¸¥§¥¯¥È¤Ø¤Î¥Ý¥¤¥ó¥¿¤« @c NULL ¤Ç¤Ê¤¯¤Æ¤Ï¤Ê¤é¤Ê¤¤¡£
1133
1134     Ãͤ¬ @c NULL ¤Ê¤é¤Ð¡¢¥Õ¥©¥ó¥È¥»¥Ã¥È¤Ï»ØÄꤵ¤ì¤Æ¤¤¤Ê¤¤¡£
1135     ¤½¤¦¤Ç¤Ê¤±¤ì¤ÐÃͤ¬»Ø¤¹¥ª¥Ö¥¸¥§¥¯¥È¤Ë»ØÄꤵ¤ì¤¿¥Õ¥©¥ó¥È¥»¥Ã¥È¤«¤éÁª¤ó¤À¥Õ¥©¥ó¥È¤Ç 
1136     M-text ¤òɽ¼¨¤¹¤ë¡£*/
1137     
1138 MSymbol Mfontset;
1139
1140 /***en
1141     @brief Key of a face property specifying hook.
1142
1143     The variable #Mhook_func is used as a key of face property.  The
1144     value must be a function of type #MFaceHookFunc, or @c NULL.
1145
1146     The value @c NULL means that the face does not specify a hook.
1147     Otherwise, the specified function is called before the face is
1148     realized.  */
1149 /***ja
1150     @brief ¥Õ¥Ã¥¯¤ò»ØÄꤹ¤ë¤¿¤á¤Î¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¡¼¤Î¥­¡¼.
1151
1152     ÊÑ¿ô #Mhook_func ¤Ï¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¤Î¥­¡¼¤È¤·¤ÆÍѤ¤¤é¤ì¤ë¡£ÃͤϠ
1153     #MFaceHookFunc ·¿¤Î´Ø¿ô¤« @c NULL ¤Ç¤Ê¤¯¤Æ¤Ï¤Ê¤é¤Ê¤¤¡£
1154
1155     Ãͤ¬ @c NULL ¤Ê¤é¤Ð¡¢¥Õ¥Ã¥¯¤Ï»ØÄꤵ¤ì¤Æ¤¤¤Ê¤¤¡£
1156     ¤½¤¦¤Ç¤Ê¤±¤ì¤Ð¥Õ¥§¡¼¥¹¤ò¼Â¸½¤¹¤ëÁ°¤Ë»ØÄꤵ¤ì¤¿´Ø¿ô¤¬¸Æ¤Ð¤ì¤ë¡£      */
1157 MSymbol Mhook_func;
1158
1159 /***en
1160     @brief Key of a face property specifying argument of hook.
1161
1162     The variable #Mhook_arg is used as a key of face property.  The
1163     value can be anything that is passed a hook function specified by
1164     the face property #Mhook_func.  */
1165 /***ja
1166     @brief ¥Õ¥Ã¥¯¤Î°ú¿ô¤ò»ØÄꤹ¤ë¤¿¤á¤Î¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¡¼¤Î¥­¡¼.
1167
1168     ÊÑ¿ô #Mhook_arg ¤Ï¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¤Î¥­¡¼¤È¤·¤ÆÍѤ¤¤é¤ì¤ë¡£
1169     Ãͤϲ¿¤Ç¤â¤è¤¯¡¢¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£ #Mhook_func ¤Ç»ØÄꤵ¤ì¤ë´Ø¿ô¤ËÅϤµ¤ì¤ë¡£ */
1170 MSymbol Mhook_arg;
1171
1172 /*** @} */
1173 /*=*/
1174
1175 /*** @ingroup m17nFace */
1176 /***en @name Variables: Possible values of #Mvideomode property of face */
1177 /***ja @name ÊÑ¿ô¡§  ¥Õ¥§¡¼¥¹¤Î #Mvideomode ¥×¥í¥Ñ¥Æ¥£¤Î²Äǽ¤ÊÃÍ */
1178 /*** @{ */
1179 /*=*/
1180
1181 /***en
1182     See the documentation of the variable #Mvideomode.  */ 
1183 /***ja
1184     ÊÑ¿ô #Mvideomode ¤ÎÀâÌÀ¤ò»²¾È¤Î¤³¤È¡£  */ 
1185 MSymbol Mnormal;
1186 MSymbol Mreverse;
1187 /*** @} */
1188 /*=*/
1189
1190 /*** @ingroup m17nFace */
1191 /***en @name Variables: Predefined faces  */
1192 /***ja @name ÊÑ¿ô: ÄêµÁºÑ¤ß¥Õ¥§¡¼¥¹  */
1193 /*** @{ */
1194 /*=*/
1195
1196 /***en
1197     @brief Normal video face.
1198
1199     The variable #mface_normal_video points to a face that has the
1200     #Mvideomode property with value #Mnormal.  The other properties
1201     are not specified.  An M-text drawn with this face appear normal
1202     colors (i.e. the foreground is drawn by foreground color, and
1203     background is drawn by background color).  */
1204 /***ja
1205     @brief É¸½à¥Ó¥Ç¥ª¥Õ¥§¡¼¥¹.
1206
1207     ÊÑ¿ô #mface_normal_video ¤Ï #Mvideomode ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤ¬ #Mnormal 
1208     ¤Ç¤¢¤ë¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£
1209     ¤³¤Î¥Õ¥§¡¼¥¹¤Çɽ¼¨¤µ¤ì¤ëM-text 
1210     ¤Ïɸ½à¤Î¿§ (¤¹¤Ê¤ï¤ÁÁ°·Ê¤ÏÁ°·Ê¿§¡¢ÇطʤÏÇØ·Ê¿§¡Ë¤ÇÉÁ¤«¤ì¤ë¡£  */
1211
1212 MFace *mface_normal_video;
1213
1214 /***en
1215     @brief Reverse video face.
1216
1217     The variable #mface_reverse_video points to a face that has the
1218     #Mvideomode property with value #Mreverse.  The other properties
1219     are not specified.  An M-text drawn with this face appear in
1220     reversed colors (i.e. the foreground is drawn by background
1221     color, and background is drawn by foreground color).  */
1222 /***ja
1223     @brief ¥ê¥Ð¡¼¥¹¥Ó¥Ç¥ª¥Õ¥§¡¼¥¹.
1224
1225     ÊÑ¿ô #mface_reverse_video ¤Ï #Mvideomode ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤ¬ 
1226     #Mreverse ¤Ç¤¢¤ë¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£
1227     ¤³¤Î¥Õ¥§¡¼¥¹¤Çɽ¼¨¤µ¤ì¤ëM-text 
1228     ¤ÏÁ°·Ê¿§¤ÈÇØ·Ê¿§¤¬Æþ¤ìÂؤï¤Ã¤Æ (¤¹¤Ê¤ï¤ÁÁ°·Ê¤ÏÇØ·Ê¿§¡¢ÇطʤÏÁ°·Ê¿§¡ËÉÁ¤«¤ì¤ë¡£  */
1229
1230 MFace *mface_reverse_video;
1231
1232 /***en
1233     @brief Underline face.
1234
1235     The variable #mface_underline points to a face that has the
1236     #Mhline property with value a pointer to an object of type
1237     #MFaceHLineProp.  The members of the object are as follows:
1238
1239 @verbatim
1240     member  value
1241     -----   -----
1242     type    MFACE_HLINE_UNDER
1243     width   1
1244     color   Mnil
1245 @endverbatim
1246
1247     The other properties are not specified.  An M-text that has this
1248     face is drawn with an underline.  */ 
1249 /***ja
1250     @brief ²¼Àþ¥Õ¥§¡¼¥¹.
1251
1252     ÊÑ¿ô #mface_underline ¤Ï #Mhline ¥×¥í¥Ñ¥Æ¥¤¤ÎÃͤ¬ #MFaceHLineProp 
1253     ·¿¥ª¥Ö¥¸¥§¥¯¥È¤Ø¤Î¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£¥ª¥Ö¥¸¥§¥¯¥È¤Î¥á¥ó¥Ð¤Ï°Ê²¼¤ÎÄ̤ꡣ
1254
1255 @verbatim
1256     ¥á¥ó¥Ð  ÃÍ
1257     -----   -----
1258     type    MFACE_HLINE_UNDER
1259     width   1
1260     color   Mnil
1261 @endverbatim
1262
1263     Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text ¤Ï²¼ÀþÉÕ¤­¤Çɽ¼¨¤µ¤ì¤ë¡£*/ 
1264
1265 MFace *mface_underline;
1266
1267 /***en
1268     @brief Medium face.
1269
1270     The variable #mface_medium points to a face that has the #Mweight
1271     property with value a symbol of name "medium".  The other
1272     properties are not specified.  An M-text that has this face is
1273     drawn with a font of medium weight.  */
1274 /***ja
1275     @brief ¥ß¥Ç¥£¥¢¥à¥Õ¥§¡¼¥¹.
1276
1277     ÊÑ¿ô #mface_medium ¤Ï #Mweight ¥×¥í¥Ñ¥Æ¥¤¤ÎÃͤ¬ "medium" 
1278     ¤È¤¤¤¦Ì¾Á°¤ò¤â¤Ä¥·¥ó¥Ü¥ë¤Ç¤¢¤ë¤è¤¦¤Ê¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£
1279     Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text
1280     ¤Ï¡¢¥ß¥Ç¥£¥¢¥à¥¦¥§¥¤¥È¤Î¥Õ¥©¥ó¥È¤Çɽ¼¨¤µ¤ì¤ë¡£  */
1281 MFace *mface_medium;
1282
1283 /***en
1284     @brief Bold face.
1285
1286     The variable #mface_bold points to a face that has the #Mweight
1287     property with value a symbol of name "bold".  The other properties
1288     are not specified.  An M-text that has this face is drawn with a
1289     font of bold weight.  */
1290 /***ja
1291     @brief ¥Ü¡¼¥ë¥É¥Õ¥§¡¼¥¹.
1292
1293     ÊÑ¿ô #mface_bold ¤Ï #Mweight ¥×¥í¥Ñ¥Æ¥¤¤ÎÃͤ¬ "bold" 
1294     ¤È¤¤¤¦Ì¾Á°¤ò¤â¤Ä¥·¥ó¥Ü¥ë¤Ç¤¢¤ë¤è¤¦¤Ê¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£
1295     Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text 
1296     ¤Ï¡¢¥Ü¡¼¥ë¥É¥Õ¥©¥ó¥È¤Çɽ¼¨¤µ¤ì¤ë¡£    */
1297
1298 MFace *mface_bold;
1299
1300 /***en
1301     @brief Italic face.
1302
1303     The variable #mface_italic points to a face that has the #Mstyle
1304     property with value a symbol of name "italic".  The other
1305     properties are not specified.  An M-text that has this face is
1306     drawn with a font of italic style.  */
1307 /***ja
1308     @brief ¥¤¥¿¥ê¥Ã¥¯¥Õ¥§¡¼¥¹.
1309
1310     ÊÑ¿ô #mface_italic ¤Ï #Mstyle ¥×¥í¥Ñ¥Æ¥¤¤ÎÃͤ¬ "italic" 
1311     ¤È¤¤¤¦Ì¾Á°¤ò¤â¤Ä¥·¥ó¥Ü¥ë¤Ç¤¢¤ë¤è¤¦¤Ê¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£
1312     Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text
1313     ¤Ï¡¢¥¤¥¿¥ê¥Ã¥¯ÂΤÇɽ¼¨¤µ¤ì¤ë¡£    */
1314
1315 MFace *mface_italic;
1316
1317 /***en
1318     @brief Bold italic face.
1319
1320     The variable #mface_bold_italic points to a face that has the
1321     #Mweight property with value a symbol of name "bold", and #Mstyle
1322     property with value a symbol of name "italic".  The other
1323     properties are not specified.  An M-text that has this face is
1324     drawn with a font of bold weight and italic style.  */
1325 /***ja
1326     @brief ¥Ü¡¼¥ë¥É¥¤¥¿¥ê¥Ã¥¯¥Õ¥§¡¼¥¹.
1327
1328     ÊÑ¿ô #mface_bold_italic ¤Ï¡¢#Mweight ¥×¥í¥Ñ¥Æ¥¤¤ÎÃͤ¬ "bold" 
1329     ¤È¤¤¤¦Ì¾Á°¤ò¤â¤Ä¥·¥ó¥Ü¥ë¤Ç¤¢¤ê¡¢¤«¤Ä #Mstyle ¥×¥í¥Ñ¥Æ¥¤¤ÎÃͤ¬ "italic" 
1330     ¤È¤¤¤¦Ì¾Á°¤ò¤â¤Ä¥·¥ó¥Ü¥ë¤Ç¤¢¤ë¤è¤¦¤Ê¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£
1331     Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text 
1332     ¤Ï¡¢¥Ü¡¼¥ë¥É¥¤¥¿¥ê¥Ã¥¯ÂΤÇɽ¼¨¤µ¤ì¤ë¡£    */
1333
1334 MFace *mface_bold_italic;
1335
1336 /***en
1337     @brief Smallest face.
1338
1339     The variable #mface_xx_small points to a face that has the #Mratio
1340     property with value 50.  The other properties are not specified.
1341     An M-text that has this face is drawn with a font whose size is
1342     50% of a normal font.  */
1343 /***ja
1344     @brief ºÇ¾®¤Î¥Õ¥§¡¼¥¹.
1345
1346     ÊÑ¿ô #mface_xx_small ¤Ï¡¢#Mratio ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤ¬ 50 
1347     ¤Ç¤¢¤ë¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£
1348     ¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text ¤Ïɸ½à¥Õ¥©¥ó¥È¤Î 50% ¤ÎÂ礭¤µ¤Î¥Õ¥©¥ó¥È¤òÍѤ¤¤Æɽ¼¨¤µ¤ì¤ë¡£
1349      */
1350
1351 MFace *mface_xx_small;
1352
1353 /***en
1354     @brief Smaller face.
1355
1356     The variable #mface_x_small points to a face that has the #Mratio
1357     property with value 66.  The other properties are not specified.
1358     An M-text that has this face is drawn with a font whose size is
1359     66% of a normal font.  */
1360 /***ja
1361     @brief ¤è¤ê¾®¤µ¤¤¥Õ¥§¡¼¥¹.
1362
1363     ÊÑ¿ô #mface_x_small ¤Ï¡¢#Mratio ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤ¬ 66 
1364     ¤Ç¤¢¤ë¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£
1365     ¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text ¤Ïɸ½à¥Õ¥©¥ó¥È¤Î 66% ¤ÎÂ礭¤µ¤Î¥Õ¥©¥ó¥È¤òÍѤ¤¤Æɽ¼¨¤µ¤ì¤ë¡£
1366      */
1367
1368 MFace *mface_x_small;
1369
1370 /***en
1371     @brief Small face.
1372
1373     The variable #mface_x_small points to a face that has the #Mratio
1374     property with value 75.  The other properties are not specified.
1375     An M-text that has this face is drawn with a font whose size is
1376     75% of a normal font.  */
1377 /***ja
1378     @brief ¾®¤µ¤¤¥Õ¥§¡¼¥¹.
1379
1380     ÊÑ¿ô #mface_small ¤Ï¡¢#Mratio ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤ¬ 75 
1381     ¤Ç¤¢¤ë¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£
1382     ¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text ¤Ïɸ½à¥Õ¥©¥ó¥È¤Î 75% ¤ÎÂ礭¤µ¤Î¥Õ¥©¥ó¥È¤òÍѤ¤¤Æɽ¼¨¤µ¤ì¤ë¡£
1383      */
1384
1385 MFace *mface_small;
1386
1387 /***en
1388     @brief Normalsize face.
1389
1390     The variable #mface_normalsize points to a face that has the
1391     #Mratio property with value 100.  The other properties are not
1392     specified.  An M-text that has this face is drawn with a font
1393     whose size is the same as a normal font.  */
1394 /***ja
1395     @brief É¸½à¤ÎÂ礭¤µ¤Î¥Õ¥§¡¼¥¹.
1396
1397     ÊÑ¿ô #mface_normalsize ¤Ï¡¢#Mratio ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤ¬ 100 
1398     ¤Ç¤¢¤ë¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£
1399     ¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text ¤Ïɸ½à¥Õ¥©¥ó¥È¤ÈƱ¤¸Â礭¤µ¤Î¥Õ¥©¥ó¥È¤òÍѤ¤¤Æɽ¼¨¤µ¤ì¤ë¡£
1400      */
1401
1402 MFace *mface_normalsize;
1403
1404 /***en
1405     @brief Large face.
1406
1407     The variable #mface_large points to a face that has the #Mratio
1408     property with value 120.  The other properties are not specified.
1409     An M-text that has this face is drawn with a font whose size is
1410     120% of a normal font.  */
1411 /***ja
1412     @brief Â礭¤¤¥Õ¥§¡¼¥¹.
1413
1414     ÊÑ¿ô #mface_large ¤Ï¡¢#Mratio ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤ¬ 120 
1415     ¤Ç¤¢¤ë¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£
1416     ¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text ¤Ïɸ½à¥Õ¥©¥ó¥È¤Î 120% ¤ÎÂ礭¤µ¤Î¥Õ¥©¥ó¥È¤òÍѤ¤¤Æɽ¼¨¤µ¤ì¤ë¡£
1417      */
1418
1419 MFace *mface_large;
1420
1421 /***en
1422     @brief Larger face.
1423
1424     The variable #mface_x_large points to a face that has the #Mratio
1425     property with value 150.  The other properties are not specified.
1426     An M-text that has this face is drawn with a font whose size is
1427     150% of a normal font.  */
1428 /***ja
1429     @brief ¤â¤Ã¤ÈÂ礭¤¤¥Õ¥§¡¼¥¹.
1430
1431     ÊÑ¿ô #mface_x_large ¤Ï¡¢#Mratio ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤ¬ 150 
1432     ¤Ç¤¢¤ë¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£
1433     ¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text ¤Ïɸ½à¥Õ¥©¥ó¥È¤Î 150% ¤ÎÂ礭¤µ¤Î¥Õ¥©¥ó¥È¤òÍѤ¤¤Æɽ¼¨¤µ¤ì¤ë¡£
1434      */
1435
1436 MFace *mface_x_large;
1437
1438 /***en
1439     @brief Largest face.
1440
1441     The variable #mface_xx_large points to a face that has the #Mratio
1442     property with value 200.  The other properties are not specified.
1443     An M-text that has this face is drawn with a font whose size is
1444     200% of a normal font.  */
1445 /***ja
1446     @brief ºÇÂç¤Î¥Õ¥§¡¼¥¹.
1447
1448     ÊÑ¿ô #mface_xx_large ¤Ï¡¢#Mratio ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤ¬ 200 
1449     ¤Ç¤¢¤ë¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£
1450     ¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text ¤Ïɸ½à¥Õ¥©¥ó¥È¤Î 200% ¤ÎÂ礭¤µ¤Î¥Õ¥©¥ó¥È¤òÍѤ¤¤Æɽ¼¨¤µ¤ì¤ë¡£
1451      */
1452
1453 MFace *mface_xx_large;
1454
1455 /***en
1456     @brief Black face.
1457
1458     The variable #mface_black points to a face that has the
1459     #Mforeground property with value a symbol of name "black".  The
1460     other properties are not specified.  An M-text that has this face
1461     is drawn with black foreground.  */
1462 /***ja 
1463     @brief ¹õ¥Õ¥§¡¼¥¹.
1464
1465     ÊÑ¿ô #mface_black ¤Ï¡¢#Mforeground ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤȤ·¤Æ "black" 
1466     ¤È¤¤¤¦Ì¾Á°¤Î¥·¥ó¥Ü¥ë¤ò»ý¤Ä¤è¤¦¤Ê¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£
1467     Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text 
1468     ¤ÏÁ°·Ê¿§¤È¤·¤Æ¹õ¤òÍѤ¤¤Æɽ¼¨¤µ¤ì¤ë¡£     */
1469
1470 MFace *mface_black;
1471
1472 /***en
1473     @brief White face.
1474
1475     The variable #mface_white points to a face that has the
1476     #Mforeground property with value a symbol of name "white".  The
1477     other properties are not specified.  An M-text that has this face
1478     is drawn with white foreground.  */
1479 /***ja
1480     @brief Çò¥Õ¥§¡¼¥¹.
1481
1482     ÊÑ¿ô #mface_white ¤Ï¡¢#Mforeground ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤȤ·¤Æ "white" 
1483     ¤È¤¤¤¦Ì¾Á°¤Î¥·¥ó¥Ü¥ë¤ò»ý¤Ä¤è¤¦¤Ê¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£
1484     Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text 
1485     ¤ÏÁ°·Ê¿§¤È¤·¤ÆÇò¤òÍѤ¤¤Æɽ¼¨¤µ¤ì¤ë¡£     */
1486
1487 MFace *mface_white;
1488
1489 /***en
1490     @brief Red face.
1491
1492     The variable #mface_red points to a face that has the
1493     #Mforeground property with value a symbol of name "red".  The
1494     other properties are not specified.  An M-text that has this face
1495     is drawn with red foreground.  */
1496 /***ja
1497     @brief ÀÖ¥Õ¥§¡¼¥¹.
1498
1499     ÊÑ¿ô #mface_red ¤Ï¡¢#Mforeground ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤȤ·¤Æ "red" 
1500     ¤È¤¤¤¦Ì¾Á°¤Î¥·¥ó¥Ü¥ë¤ò»ý¤Ä¤è¤¦¤Ê¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£
1501     Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text 
1502     ¤ÏÁ°·Ê¿§¤È¤·¤ÆÀÖ¤òÍѤ¤¤Æɽ¼¨¤µ¤ì¤ë¡£  */
1503
1504 MFace *mface_red;
1505
1506 /***en
1507     @brief Green face.
1508
1509     The variable #mface_green points to a face that has the
1510     #Mforeground property with value a symbol of name "green".  The
1511     other properties are not specified.  An M-text that has this face
1512     is drawn with green foreground.  */
1513 /***ja
1514     @brief ÎÐ¥Õ¥§¡¼¥¹.
1515
1516     ÊÑ¿ô #mface_green ¤Ï¡¢#Mforeground ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤȤ·¤Æ "green" 
1517     ¤È¤¤¤¦Ì¾Á°¤Î¥·¥ó¥Ü¥ë¤ò»ý¤Ä¤è¤¦¤Ê¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£
1518     Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text 
1519     ¤ÏÁ°·Ê¿§¤È¤·¤ÆÎФòÍѤ¤¤Æɽ¼¨¤µ¤ì¤ë¡£  */
1520
1521 MFace *mface_green;
1522
1523 /***en
1524     @brief Blue face.
1525
1526     The variable #mface_blue points to a face that has the
1527     #Mforeground property with value a symbol of name "blue".  The
1528     other properties are not specified.  An M-text that has this face
1529     is drawn with blue foreground.  */
1530 /***ja
1531     @brief ÀÄ¥Õ¥§¡¼¥¹.
1532
1533     ÊÑ¿ô #mface_blue ¤Ï¡¢#Mforeground ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤȤ·¤Æ "blue" 
1534     ¤È¤¤¤¦Ì¾Á°¤Î¥·¥ó¥Ü¥ë¤ò»ý¤Ä¤è¤¦¤Ê¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£
1535     Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text 
1536     ¤ÏÁ°·Ê¿§¤È¤·¤ÆÀĤòÍѤ¤¤Æɽ¼¨¤µ¤ì¤ë¡£  */
1537
1538 MFace *mface_blue;
1539
1540 /***en
1541     @brief Cyan face.
1542
1543     The variable #mface_cyan points to a face that has the
1544     #Mforeground property with value a symbol of name "cyan".  The
1545     other properties are not specified.  An M-text that has this face
1546     is drawn with cyan foreground.  */
1547 /***ja
1548     @brief ¥·¥¢¥ó¥Õ¥§¡¼¥¹.
1549
1550     ÊÑ¿ô #mface_cyan ¤Ï¡¢#Mforeground ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤȤ·¤Æ "cyan"
1551     ¤È¤¤¤¦Ì¾Á°¤Î¥·¥ó¥Ü¥ë¤ò»ý¤Ä¤è¤¦¤Ê¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£
1552     Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text 
1553     ¤ÏÁ°·Ê¿§¤È¤·¤Æ¥·¥¢¥ó¤òÍѤ¤¤Æɽ¼¨¤µ¤ì¤ë¡£  */
1554
1555 MFace *mface_cyan;
1556
1557 /***en
1558     @brief yellow face.
1559
1560     The variable #mface_yellow points to a face that has the
1561     #Mforeground property with value a symbol of name "yellow".  The
1562     other properties are not specified.  An M-text that has this face
1563     is drawn with yellow foreground.  */
1564
1565 /***ja
1566     @brief ²«¥Õ¥§¡¼¥¹.
1567
1568     ÊÑ¿ô #mface_yellow ¤Ï¡¢#Mforeground ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤȤ·¤Æ "yellow" 
1569     ¤È¤¤¤¦Ì¾Á°¤Î¥·¥ó¥Ü¥ë¤ò»ý¤Ä¤è¤¦¤Ê¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£
1570     Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text 
1571     ¤ÏÁ°·Ê¿§¤È¤·¤Æ²«¿§¤òÍѤ¤¤Æɽ¼¨¤µ¤ì¤ë¡£  */
1572
1573 MFace *mface_yellow;
1574
1575 /***en
1576     @brief Magenta face.
1577
1578     The variable #mface_magenta points to a face that has the
1579     #Mforeground property with value a symbol of name "magenta".  The
1580     other properties are not specified.  An M-text that has this face
1581     is drawn with magenta foreground.  */
1582
1583 /***ja
1584     @brief ¥Þ¥¼¥ó¥¿¥Õ¥§¡¼¥¹.
1585
1586     ÊÑ¿ô #mface_magenta ¤Ï¡¢#Mforeground ¥×¥í¥Ñ¥Æ¥£¤ÎÃͤȤ·¤Æ 
1587     "magenta" ¤È¤¤¤¦Ì¾Á°¤Î¥·¥ó¥Ü¥ë¤ò»ý¤Ä¤è¤¦¤Ê¥Õ¥§¡¼¥¹¤ò»Ø¤¹¥Ý¥¤¥ó¥¿¤Ç¤¢¤ë¡£
1588     Â¾¤Î¥×¥í¥Ñ¥Æ¥£¤Ï»ØÄꤵ¤ì¤Ê¤¤¡£¤³¤Î¥Õ¥§¡¼¥¹¤ò»ý¤Ä M-text 
1589     ¤ÏÁ°·Ê¿§¤È¤·¤Æ¥Þ¥¼¥ó¥¿¤òÍѤ¤¤Æɽ¼¨¤µ¤ì¤ë¡£  */
1590
1591 MFace *mface_magenta;
1592
1593 /*** @} */
1594 /*=*/
1595
1596 /***en @name Variables: The other symbols for face handling.  */
1597 /***ja @name ÊÑ¿ô: ¥Õ¥§¡¼¥¹¤ò¼è¤ê°·¤¦¤¿¤á¤Î¤½¤Î¾¤Î¥·¥ó¥Ü¥ë  */
1598 /*** @{ */
1599 /*=*/
1600
1601 /***en
1602     @brief Key of a text property specifying a face.
1603
1604     The variable #Mface is a symbol of name <tt>"face"</tt>.  A text
1605     property whose key is this symbol must have a pointer to an object
1606     of type #MFace.  This is a managing key.  */
1607
1608 /***ja
1609     @brief ¥Õ¥§¡¼¥¹¤ò»ØÄꤹ¤ë¥Æ¥­¥¹¥È¥×¥í¥Ñ¥Æ¥£¤Î¥­¡¼.
1610
1611     ÊÑ¿ô #Mface ¤Ï <tt>"face"</tt> 
1612     ¤È¤¤¤¦Ì¾Á°¤ò»ý¤Ä¥·¥ó¥Ü¥ë¤Ç¤¢¤ë¡£¤³¤Î¥·¥ó¥Ü¥ë¤ò¥­¡¼¤È¤¹¤ë¥Æ¥­¥¹¥È¥×¥í¥Ñ¥Æ¥£¤Ï¡¢
1613     #MFace ·¿¤Î¥ª¥Ö¥¸¥§¥¯¥È¤Ø¤Î¥Ý¥¤¥ó¥¿¤ò»ý¤¿¤Ê¤±¤ì¤Ð¤Ê¤é¤Ê¤¤¡£
1614     ¤³¤ì¤Ï´ÉÍý¥­¡¼¤Ç¤¢¤ë¡£  */
1615
1616 MSymbol Mface;
1617 /*=*/
1618 /*** @} */
1619 /*=*/
1620
1621 /***en
1622     @brief Create a new face.
1623
1624     The mface () function creates a new face object that specifies no
1625     property.
1626
1627     @return
1628     This function returns a pointer to the created face.  */
1629
1630 /***ja
1631     @brief ¿·¤·¤¤¥Õ¥§¡¼¥¹¤ò¤Ä¤¯¤ë.
1632
1633     ´Ø¿ô mface () 
1634     ¤Ï¥×¥í¥Ñ¥Æ¥£¤ò°ìÀÚ»ý¤¿¤Ê¤¤¿·¤·¤¤¥Õ¥§¡¼¥¹¥ª¥Ö¥¸¥§¥¯¥È¤òºî¤ë¡£
1635
1636     @return
1637     ¤³¤Î´Ø¿ô¤Ïºî¤Ã¤¿¥Õ¥§¡¼¥¹¤Ø¤Î¥Ý¥¤¥ó¥¿¤òÊÖ¤¹¡£  */
1638
1639 MFace *
1640 mface ()
1641 {
1642   MFace *face;
1643
1644   M17N_OBJECT (face, free_face, MERROR_FACE);
1645   face->frame_list = mplist ();
1646   M17N_OBJECT_REGISTER (face_table, face);
1647   return face;
1648 }
1649
1650 /*=*/
1651
1652 /***en
1653     @brief Make a copy of a face.
1654
1655     The mface_copy () function makes a copy of $FACE and returns a
1656     pointer to the created copy.  */
1657
1658 /***ja
1659     @brief ¥Õ¥§¡¼¥¹¤Î¥³¥Ô¡¼¤òºî¤ë.
1660
1661     ´Ø¿ô mface_copy () ¤Ï¥Õ¥§¡¼¥¹ $FACE 
1662     ¤Î¥³¥Ô¡¼¤òºî¤ê¡¢¤½¤Î¥³¥Ô¡¼¤Ø¤Î¥Ý¥¤¥ó¥¿¤òÊÖ¤¹¡£  */
1663
1664 MFace *
1665 mface_copy (MFace *face)
1666 {
1667   MFace *copy;
1668
1669   MSTRUCT_CALLOC (copy, MERROR_FACE);
1670   *copy = *face;
1671   copy->control.ref_count = 1;
1672   M17N_OBJECT_REGISTER (face_table, copy);
1673   copy->frame_list = mplist ();
1674   if (copy->property[MFACE_FONTSET])
1675     M17N_OBJECT_REF (copy->property[MFACE_FONTSET]);
1676   return copy;
1677 }
1678
1679 /*=*/
1680 /***en
1681     @brief Compare faces.
1682
1683     The mface_equal () function compares faces $FACE1 and $FACE2.
1684
1685     @return If two faces have the same property values, return 1.
1686     Otherwise return 0.  */
1687
1688 int
1689 mface_equal (MFace *face1, MFace *face2)
1690 {
1691   MFaceHLineProp *hline1, *hline2;
1692   MFaceBoxProp *box1, *box2;
1693   int i;
1694
1695   if (face1 == face2)
1696     return 1;
1697   if (memcmp (face1->property, face2->property, sizeof face1->property) == 0)
1698     return 1;
1699   for (i = MFACE_FOUNDRY; i <= MFACE_BACKGROUND; i++)
1700     if (face1->property[i] != face2->property[i])
1701       return 0;
1702   for (i = MFACE_VIDEOMODE; i <= MFACE_RATIO; i++)
1703     if (face1->property[i] != face2->property[i])
1704       return 0;
1705   hline1 = (MFaceHLineProp *) face1->property[MFACE_HLINE];
1706   hline2 = (MFaceHLineProp *) face2->property[MFACE_HLINE];
1707   if (hline1 != hline2)
1708     {
1709       if (! hline1 || ! hline2)
1710         return 0;
1711       if (memcmp (hline1, hline2, sizeof (MFaceHLineProp)) != 0)
1712         return 0;
1713     }
1714   box1 = (MFaceBoxProp *) face1->property[MFACE_BOX];
1715   box2 = (MFaceBoxProp *) face2->property[MFACE_BOX];
1716   if (box1 != box2)
1717     {
1718       if (! box1 || ! box2)
1719         return 0;
1720       if (memcmp (box1, box2, sizeof (MFaceBoxProp)) != 0)
1721         return 0;
1722     }
1723   return 1;
1724 }
1725
1726
1727 /*=*/
1728 /***en
1729     @brief Merge faces.
1730
1731     The mface_merge () functions merges the properties of face $SRC
1732     into $DST.
1733
1734     @return
1735     This function returns $DST.  */
1736
1737 /***ja
1738     @brief ¥Õ¥§¡¼¥¹¤òÅý¹ç¤¹¤ë.
1739
1740     ´Ø¿ô mface_merge () ¤Ï¡¢¥Õ¥§¡¼¥¹ $SRC ¤Î¥×¥í¥Ñ¥Æ¥£¤ò¥Õ¥§¡¼¥¹ $DST 
1741     ¤ËÅý¹ç¤¹¤ë¡£
1742
1743     @return
1744     ¤³¤Î´Ø¿ô¤Ï $DST ¤òÊÖ¤¹¡£  */
1745
1746 MFace *
1747 mface_merge (MFace *dst, MFace *src)
1748 {
1749   int i;
1750   MPlist *plist;
1751
1752   for (i = 0; i < MFACE_PROPERTY_MAX; i++)
1753     if (src->property[i])
1754       {
1755         if (i == MFACE_FONTSET)
1756           {
1757             M17N_OBJECT_UNREF (dst->property[i]);
1758             M17N_OBJECT_REF (src->property[i]);
1759           }
1760         dst->property[i] = src->property[i];
1761       }
1762
1763   MPLIST_DO (plist, dst->frame_list)
1764     {
1765       MFrame *frame = MPLIST_VAL (plist);
1766
1767       frame->tick++;
1768       if (dst == frame->face)
1769         mface__update_frame_face (frame);
1770     }
1771
1772   return dst;
1773 }
1774
1775 /*=*/
1776
1777 /***en
1778     @brief Make a face from a font.
1779
1780     The mface_from_font () function return a newly created face while
1781     reflecting the properties of $FONT in its properties.   */
1782
1783 /***ja
1784     @brief ¥Õ¥©¥ó¥È¤«¤é¥Õ¥§¡¼¥¹¤òºî¤ë.
1785
1786     ´Ø¿ô mface_from_font () ¤Ï¥Õ¥©¥ó¥È $FONT 
1787     ¤Î¥×¥í¥Ñ¥Æ¥£¤ò¥×¥í¥Ñ¥Æ¥£¤È¤·¤Æ»ý¤Ä¿·¤·¤¤¥Õ¥§¡¼¥¹¤òºî¤ê¡¢¤½¤ì¤òÊÖ¤¹¡£  */
1788
1789 MFace *
1790 mface_from_font (MFont *font)
1791 {
1792   MFace *face = mface ();
1793
1794   face->property[MFACE_FOUNDRY] = mfont_get_prop (font, Mfoundry);
1795   face->property[MFACE_FAMILY] = mfont_get_prop (font, Mfamily);
1796   face->property[MFACE_WEIGHT] = mfont_get_prop (font, Mweight);
1797   face->property[MFACE_STYLE] = mfont_get_prop (font, Mstyle);
1798   face->property[MFACE_STRETCH] = mfont_get_prop (font, Mstretch);
1799   face->property[MFACE_ADSTYLE] = mfont_get_prop (font, Madstyle);
1800   face->property[MFACE_SIZE] = mfont_get_prop (font, Msize);
1801   return face;
1802 }
1803
1804 /*=*/
1805
1806 /***en
1807     @brief Get the value of a face property.
1808
1809     The mface_get_prop () function returns the value of the face
1810     property whose key is $KEY in face $FACE.  $KEY must be one of the
1811     followings:
1812
1813         #Mforeground, #Mbackground, #Mvideomode, #Mhline, #Mbox,
1814         #Mfoundry, #Mfamily, #Mweight, #Mstyle, #Mstretch, #Madstyle,
1815         #Msize, #Mfontset, #Mratio, #Mhook_func, #Mhook_arg
1816
1817     @return
1818     The actual type of the returned value depends of $KEY.  See
1819     documentation of the above keys.  If an error is detected, it
1820     returns @c NULL and assigns an error code to the external variable
1821     #merror_code.  */
1822
1823 /***ja
1824     @brief ¥Õ¥§¡¼¥¹¤Î¥×¥í¥Ñ¥Æ¥£¤ÎÃͤòÆÀ¤ë.
1825
1826     ´Ø¿ô mface_get_prop () ¤Ï¡¢¥Õ¥§¡¼¥¹ $FACE 
1827     ¤¬»ý¤Ä¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¤ÎÆâ¡¢¥­¡¼¤¬ $KEY ¤Ç¤¢¤ë¤â¤Î¤ÎÃͤòÊÖ¤¹¡£
1828     $KEY ¤Ï²¼µ­¤Î¤¤¤º¤ì¤«¤Ç¤Ê¤±¤ì¤Ð¤Ê¤é¤Ê¤¤¡£
1829
1830         #Mforeground, #Mbackground, #Mvideomode, #Mhline, #Mbox,
1831         #Mfoundry, #Mfamily, #Mweight, #Mstyle, #Mstretch, #Madstyle,
1832         #Msize, #Mfontset, #Mratio, #Mhook_arg
1833
1834     @return 
1835     Ìá¤êÃͤη¿¤Ï $KEY ¤Ë°Í¸¤¹¤ë¡£¾åµ­¤Î¥­¡¼¤ÎÀâÌÀ¤ò»²¾È¤¹¤ë¤³¤È¡£
1836     ¥¨¥é¡¼¤¬¸¡½Ð¤µ¤ì¤¿¾ì¹ç¤Ï @c NULL ¤òÊÖ¤·¡¢³°ÉôÊÑ¿ô #merror_code 
1837     ¤Ë¥¨¥é¡¼¥³¡¼¥É¤òÀßÄꤹ¤ë¡£  */
1838
1839 /***
1840     @seealso
1841     mface_put_prop (), mface_put_hook ()
1842
1843     @errors
1844     @c MERROR_FACE  */
1845
1846 void *
1847 mface_get_prop (MFace *face, MSymbol key)
1848 {
1849   int index = (int) msymbol_get (key, M_face_prop_index) - 1;
1850
1851   if (index < 0)
1852     {
1853       if (key == Mhook_func)
1854         /* This unsafe code is for backward compatiblity.  */
1855         return *(void **) &face->hook;
1856       MERROR (MERROR_FACE, NULL);
1857     }
1858   return face->property[index];
1859 }
1860
1861 /*=*/
1862
1863 /***en
1864     @brief Get the hook function of a face.
1865
1866     The mface_get_hook () function returns the hook function of face
1867     $FACE.  */
1868
1869 /***ja
1870     @brief ¥Õ¥§¡¼¥¹¤Î¥Õ¥Ã¥¯´Ø¿ô¤òÆÀ¤ë.
1871
1872     ´Ø¿ô mface_get_hook () ¤Ï¥Õ¥§¡¼¥¹ $FACE ¤Î¥Õ¥Ã¥¯´Ø¿ô¤òÊÖ¤¹¡£ */
1873
1874 MFaceHookFunc
1875 mface_get_hook (MFace *face)
1876 {
1877   return face->hook;
1878 }
1879
1880 /*=*/
1881
1882 /***en
1883     @brief Set a value of a face property.
1884
1885     The mface_put_prop () function assigns $VAL to the property whose
1886     key is $KEY in face $FACE.  $KEY must be one the followings:
1887
1888         #Mforeground, #Mbackground, #Mvideomode, #Mhline, #Mbox,
1889         #Mfoundry, #Mfamily, #Mweight, #Mstyle, #Mstretch, #Madstyle,
1890         #Msize, #Mfontset, #Mratio, #Mhook_func, #Mhook_arg
1891
1892     Among them, font related properties (#Mfoundry through #Msize) are
1893     used as the default values when a font in the fontset of $FACE
1894     does not specify those values.
1895
1896     The actual type of the returned value depends of $KEY.  See
1897     documentation of the above keys.
1898
1899     @return
1900     If the operation was successful, mface_put_prop () returns 0.
1901     Otherwise it returns -1 and assigns an error code to the external
1902     variable #merror_code.  */
1903
1904 /***ja
1905     @brief ¥Õ¥§¡¼¥¹¥×¥í¥Ñ¥Æ¥£¤ÎÃͤòÀßÄꤹ¤ë.
1906
1907     ´Ø¿ô mface_put_prop () ¤Ï¡¢¥Õ¥§¡¼¥¹ $FACE Æâ¤Ç¥­¡¼¤¬ $KEY 
1908     ¤Ç¤¢¤ë¥×¥í¥Ñ¥Æ¥£¤ÎÃͤò $VAL ¤ËÀßÄꤹ¤ë¡£$KEY 
1909     ¤Ï°Ê²¼¤Î¤¤¤º¤ì¤«¤Ç¤Ê¤¯¤Æ¤Ï¤Ê¤é¤Ê¤¤¡£
1910
1911         #Mforeground, #Mbackground, #Mvideomode, #Mhline, #Mbox,
1912         #Mfoundry, #Mfamily, #Mweight, #Mstyle, #Mstretch, #Madstyle,
1913         #Msize, #Mfontset, #Mratio, #Mhook_func, #Mhook_arg.
1914
1915     ¤³¤ì¤é¤Î¤¦¤Á¤Î¡¢¥Õ¥©¥ó¥È´ØÏ¢¤Î¥×¥í¥Ñ¥Æ¥£ (#Mfamily ¤«¤é #Msize 
1916     ¤Þ¤Ç) ¤Ï¡¢¥Õ¥§¡¼¥¹¤Î¥Õ¥©¥ó¥È¥»¥Ã¥ÈÃæ¤Î¥Õ¥©¥ó¥È¤Ë´Ø¤¹¤ë¥Ç¥Õ¥©¥ë¥ÈÃͤȤʤꡢ¸Ä¡¹¤Î¥Õ¥©¥ó¥È¤¬Ãͤò»ØÄꤷ¤Ê¤«¤Ã¤¿¾ì¹ç¤ËÍѤ¤¤é¤ì¤ë¡£
1917
1918     Ìá¤êÃͤη¿¤Ï $KEY ¤Ë°Í¸¤¹¤ë¡£¾åµ­¤Î¥­¡¼¤ÎÀâÌÀ¤ò»²¾È¤¹¤ë¤³¤È¡£
1919
1920     @return
1921     ½èÍý¤¬À®¸ù¤·¤¿¾ì¹ç¡¢mface_put_prop () ¤Ï 0 ¤òÊÖ¤¹¡£¼ºÇÔ¤·¤¿¾ì¹ç¤Ï 
1922     -1 ¤òÊÖ¤·¡¢³°ÉôÊÑ¿ô #merror_code ¤Ë¥¨¥é¡¼¥³¡¼¥É¤òÀßÄꤹ¤ë¡£  */
1923
1924 /***
1925     @seealso
1926     mface_get_prop ()
1927
1928     @errors
1929     @c MERROR_FACE  */
1930
1931 int
1932 mface_put_prop (MFace *face, MSymbol key, void *val)
1933 {
1934   int index = (int) msymbol_get (key, M_face_prop_index) - 1;
1935   MPlist *plist;
1936
1937   if (key == Mhook_func)
1938     {
1939       /* This unsafe code is for backward compatiblity.  */
1940       if (*(void **) &face->hook == val)
1941         return 0;
1942       *(void **) &face->hook = val;
1943     }
1944   else
1945     {
1946       if (index < 0)
1947         MERROR (MERROR_FACE, -1);
1948       if (key == Mfontset)
1949         {
1950           if (face->property[index])
1951             M17N_OBJECT_UNREF (face->property[index]);
1952           M17N_OBJECT_REF (val);
1953         }
1954       else if (key == Mhline)
1955         val = get_hline_create (val);
1956       else if (key == Mbox)
1957         val = get_box_create (val);
1958
1959       if (face->property[index] == val)
1960         return 0;
1961       face->property[index] = val;
1962     }
1963
1964   MPLIST_DO (plist, face->frame_list)
1965     {
1966       MFrame *frame = MPLIST_VAL (plist);
1967
1968       frame->tick++;
1969       if (face == frame->face)
1970         mface__update_frame_face (frame);
1971     }
1972
1973   return 0;
1974 }
1975
1976 /*=*/
1977
1978 /***en
1979     @brief Set a hook function to a face.
1980
1981     The mface_set_hook () function sets the hook function of face
1982     $FACE to $FUNC.  */
1983
1984 /***ja
1985     @brief ¥Õ¥§¡¼¥¹¤Î¥Õ¥Ã¥¯´Ø¿ô¤òÀßÄꤹ¤ë.
1986
1987     ´Ø¿ô mface_set_hook () ¤Ï¡¢¥Õ¥§¡¼¥¹ $FACE ¤Î¥Õ¥Ã¥¯´Ø¿ô¤ò$FUNC ¤ËÀß
1988     Äꤹ¤ë¡£  */
1989
1990 int
1991 mface_put_hook (MFace *face, MFaceHookFunc func)
1992 {
1993   if (face->hook != func)
1994     {
1995       MPlist *plist;
1996       face->hook = func;
1997
1998       MPLIST_DO (plist, face->frame_list)
1999         {
2000           MFrame *frame = MPLIST_VAL (plist);
2001
2002           frame->tick++;
2003           if (face == frame->face)
2004             mface__update_frame_face (frame);
2005         }
2006     }
2007   return 0;
2008 }
2009
2010 /*=*/
2011
2012 /***en
2013     @brief Update a face.
2014
2015     The mface_update () function update face $FACE on frame $FRAME by
2016     calling a hook function of $FACE (if any).  */
2017
2018 /***ja
2019     @brief ¥Õ¥§¡¼¥¹¤ò¹¹¿·¤¹¤ë.
2020
2021     ´Ø¿ô mface_update () ¤Ï¥Õ¥ì¡¼¥à $FRAME ¤Î¥Õ¥§¡¼¥¹ $FACE ¤ò $FACE 
2022     ¤Î¥Õ¥Ã¥¯´Ø¿ô¤ò¡Ê¤¢¤ì¤Ð¡Ë¸Æ¤ó¤Ç¹¹¿·¤¹¤ë¡£  */
2023
2024 void
2025 mface_update (MFrame *frame, MFace *face)
2026 {
2027   MFaceHookFunc func = face->hook;
2028   MPlist *rface_list;
2029   MRealizedFace *rface;
2030
2031   if (func && func != noop_hook)
2032     {
2033       MPLIST_DO (rface_list, frame->realized_face_list)
2034         {
2035           rface = MPLIST_VAL (rface_list);
2036           if (rface->face.hook == func)
2037             (func) (&(rface->face), rface->face.property[MFACE_HOOK_ARG],
2038                     rface->info);
2039         }
2040     }
2041 }
2042 /*=*/
2043
2044 /*** @} */
2045 /*=*/
2046
2047 /*** @addtogroup m17nDebug */
2048 /*** @{  */
2049 /*=*/
2050
2051 /***en
2052     @brief Dump a face.
2053
2054     The mdebug_dump_face () function prints face $FACE in a human readable
2055     way to the stderr.  $INDENT specifies how many columns to indent
2056     the lines but the first one.
2057
2058     @return
2059     This function returns $FACE.  */
2060
2061 /***ja
2062     @brief ¥Õ¥§¡¼¥¹¤ò¥À¥ó¥×¤¹¤ë.
2063
2064     ´Ø¿ô mdebug_dump_face () ¤Ï¥Õ¥§¡¼¥¹ $FACE ¤ò stderr 
2065     ¤Ë¿Í´Ö¤Ë²ÄÆɤʷÁ¤Ç°õºþ¤¹¤ë¡£ $INDENT ¤Ï£²¹ÔÌܰʹߤΥ¤¥ó¥Ç¥ó¥È¤ò»ØÄꤹ¤ë¡£
2066
2067     @return
2068     ¤³¤Î´Ø¿ô¤Ï $FACE ¤òÊÖ¤¹¡£  */
2069
2070 MFace *
2071 mdebug_dump_face (MFace *face, int indent)
2072 {
2073   char *prefix = (char *) alloca (indent + 1);
2074   MFont spec;
2075
2076   memset (prefix, 32, indent);
2077   prefix[indent] = 0;
2078   mfont__set_spec_from_face (&spec, face);
2079   fprintf (stderr, "(face font:\"");
2080   mdebug_dump_font (&spec);
2081   fprintf (stderr, "\"\n %s  fore:%s back:%s", prefix,
2082            msymbol_name ((MSymbol) face->property[MFACE_FOREGROUND]),
2083            msymbol_name ((MSymbol) face->property[MFACE_BACKGROUND]));
2084   if (face->property[MFACE_FONTSET])
2085     fprintf (stderr, " non-default-fontset");
2086   fprintf (stderr, " hline:%s", face->property[MFACE_HLINE] ? "yes" : "no");
2087   fprintf (stderr, " box:%s)", face->property[MFACE_BOX] ? "yes" : "no");
2088   return face;
2089 }
2090
2091 /*** @} */
2092
2093 /*
2094   Local Variables:
2095   coding: euc-japan
2096   End:
2097 */