diff options
| author | Kenichi Handa | 2008-06-13 02:18:59 +0000 |
|---|---|---|
| committer | Kenichi Handa | 2008-06-13 02:18:59 +0000 |
| commit | 4007dd1cf6dbd6f2cb5321aa4c7baa27291c5c41 (patch) | |
| tree | 68e35151e18ddbaf10dce30c244b680cf900fd05 /src | |
| parent | 53aaf1e22f415b058b27ebd2c0c3f97727d54bcd (diff) | |
| download | emacs-4007dd1cf6dbd6f2cb5321aa4c7baa27291c5c41.tar.gz emacs-4007dd1cf6dbd6f2cb5321aa4c7baa27291c5c41.zip | |
(font_score): Delete arg alternate_families. Check only
weight, slant, width, and size.
(font_sort_entites): Adjusted for the above change. Reflect the
order of font-driver to scores.
(font_list_entities): Don't check alternate_familes here.
(font_clear_prop): Handle foundry.
(font_update_lface): Don't parse "foundry-family" form here.
Handle FONT_FOUNDRY_INDEX.
(font_find_for_lface): Likewise. Handle alternate families here.
(font_open_for_lface): Pay attention to size in ENTITY.
(font_open_by_name): Simplified by calling font_load_for_lface.
(free_font_driver_list): Delete it.
(font_update_drivers): Preserve the order of backends.
(syms_of_font): Setting of sort_shift_bits adjusted for the change
of font_score and font_sort_entites.
Diffstat (limited to 'src')
| -rw-r--r-- | src/font.c | 452 |
1 files changed, 213 insertions, 239 deletions
diff --git a/src/font.c b/src/font.c index 5fd2abe5641..cfe6e41ac28 100644 --- a/src/font.c +++ b/src/font.c | |||
| @@ -2074,7 +2074,7 @@ font_prepare_composition (cmp, f) | |||
| 2074 | 2074 | ||
| 2075 | /* Font sorting */ | 2075 | /* Font sorting */ |
| 2076 | 2076 | ||
| 2077 | static unsigned font_score P_ ((Lisp_Object, Lisp_Object *, Lisp_Object)); | 2077 | static unsigned font_score P_ ((Lisp_Object, Lisp_Object *)); |
| 2078 | static int font_compare P_ ((const void *, const void *)); | 2078 | static int font_compare P_ ((const void *, const void *)); |
| 2079 | static Lisp_Object font_sort_entites P_ ((Lisp_Object, Lisp_Object, | 2079 | static Lisp_Object font_sort_entites P_ ((Lisp_Object, Lisp_Object, |
| 2080 | Lisp_Object, Lisp_Object, | 2080 | Lisp_Object, Lisp_Object, |
| @@ -2084,14 +2084,10 @@ static Lisp_Object font_sort_entites P_ ((Lisp_Object, Lisp_Object, | |||
| 2084 | font-spec. The score value is 32 bit (`unsigned'), and the smaller | 2084 | font-spec. The score value is 32 bit (`unsigned'), and the smaller |
| 2085 | the value is, the closer the font is to the font-spec. | 2085 | the value is, the closer the font is to the font-spec. |
| 2086 | 2086 | ||
| 2087 | The highest 2 bits of the score is used for FAMILY. The exact | 2087 | The lowest 2 bits of the score is used for driver type. The font |
| 2088 | match is 0, match with one of face-font-family-alternatives is | 2088 | available by the most preferred font driver is 0. |
| 2089 | nonzero. | ||
| 2090 | 2089 | ||
| 2091 | The next 2 bits of the score is used for the atomic properties | 2090 | Each 7-bit in the higher 28 bits are used for numeric properties |
| 2092 | FOUNDRY and ADSTYLE respectively. | ||
| 2093 | |||
| 2094 | Each 7-bit in the lower 28 bits are used for numeric properties | ||
| 2095 | WEIGHT, SLANT, WIDTH, and SIZE. */ | 2091 | WEIGHT, SLANT, WIDTH, and SIZE. */ |
| 2096 | 2092 | ||
| 2097 | /* How many bits to shift to store the difference value of each font | 2093 | /* How many bits to shift to store the difference value of each font |
| @@ -2107,43 +2103,12 @@ static int sort_shift_bits[FONT_SIZE_INDEX + 1]; | |||
| 2107 | alternate family names for AREF (SPEC_PROP, FONT_FAMILY_INDEX). */ | 2103 | alternate family names for AREF (SPEC_PROP, FONT_FAMILY_INDEX). */ |
| 2108 | 2104 | ||
| 2109 | static unsigned | 2105 | static unsigned |
| 2110 | font_score (entity, spec_prop, alternate_families) | 2106 | font_score (entity, spec_prop) |
| 2111 | Lisp_Object entity, *spec_prop; | 2107 | Lisp_Object entity, *spec_prop; |
| 2112 | Lisp_Object alternate_families; | ||
| 2113 | { | 2108 | { |
| 2114 | unsigned score = 0; | 2109 | unsigned score = 0; |
| 2115 | int i; | 2110 | int i; |
| 2116 | 2111 | ||
| 2117 | /* Score three atomic fields. Maximum difference is 1 (family is 3). */ | ||
| 2118 | for (i = FONT_FOUNDRY_INDEX; i <= FONT_ADSTYLE_INDEX; i++) | ||
| 2119 | if (i != FONT_REGISTRY_INDEX | ||
| 2120 | && ! NILP (spec_prop[i]) && ! EQ (AREF (entity, i), spec_prop[i])) | ||
| 2121 | { | ||
| 2122 | Lisp_Object entity_str = SYMBOL_NAME (AREF (entity, i)); | ||
| 2123 | Lisp_Object spec_str = SYMBOL_NAME (spec_prop[i]); | ||
| 2124 | |||
| 2125 | if (xstrcasecmp (SDATA (spec_str), SDATA (entity_str))) | ||
| 2126 | { | ||
| 2127 | if (i == FONT_FAMILY_INDEX && CONSP (alternate_families)) | ||
| 2128 | { | ||
| 2129 | int j; | ||
| 2130 | |||
| 2131 | for (j = 1; CONSP (alternate_families); | ||
| 2132 | j++, alternate_families = XCDR (alternate_families)) | ||
| 2133 | { | ||
| 2134 | spec_str = XCAR (alternate_families); | ||
| 2135 | if (xstrcasecmp (SDATA (spec_str), SDATA (entity_str)) == 0) | ||
| 2136 | break; | ||
| 2137 | } | ||
| 2138 | if (j > 3) | ||
| 2139 | j = 3; | ||
| 2140 | score |= j << sort_shift_bits[i]; | ||
| 2141 | } | ||
| 2142 | else | ||
| 2143 | score |= 1 << sort_shift_bits[i]; | ||
| 2144 | } | ||
| 2145 | } | ||
| 2146 | |||
| 2147 | /* Score three style numeric fields. Maximum difference is 127. */ | 2112 | /* Score three style numeric fields. Maximum difference is 127. */ |
| 2148 | for (i = FONT_WEIGHT_INDEX; i <= FONT_WIDTH_INDEX; i++) | 2113 | for (i = FONT_WEIGHT_INDEX; i <= FONT_WIDTH_INDEX; i++) |
| 2149 | if (! NILP (spec_prop[i]) && ! EQ (AREF (entity, i), spec_prop[i])) | 2114 | if (! NILP (spec_prop[i]) && ! EQ (AREF (entity, i), spec_prop[i])) |
| @@ -2214,16 +2179,18 @@ font_sort_entites (vec, prefer, frame, spec, best_only) | |||
| 2214 | Lisp_Object prefer_prop[FONT_SPEC_MAX]; | 2179 | Lisp_Object prefer_prop[FONT_SPEC_MAX]; |
| 2215 | int len, i; | 2180 | int len, i; |
| 2216 | struct font_sort_data *data; | 2181 | struct font_sort_data *data; |
| 2217 | Lisp_Object alternate_families = Qnil; | ||
| 2218 | unsigned best_score; | 2182 | unsigned best_score; |
| 2219 | Lisp_Object best_entity; | 2183 | Lisp_Object best_entity, driver_type; |
| 2184 | int driver_order; | ||
| 2185 | struct frame *f = XFRAME (frame); | ||
| 2186 | struct font_driver_list *list; | ||
| 2220 | USE_SAFE_ALLOCA; | 2187 | USE_SAFE_ALLOCA; |
| 2221 | 2188 | ||
| 2222 | len = ASIZE (vec); | 2189 | len = ASIZE (vec); |
| 2223 | if (len <= 1) | 2190 | if (len <= 1) |
| 2224 | return best_only ? AREF (vec, 0) : vec; | 2191 | return best_only ? AREF (vec, 0) : vec; |
| 2225 | 2192 | ||
| 2226 | for (i = FONT_FOUNDRY_INDEX; i <= FONT_DPI_INDEX; i++) | 2193 | for (i = FONT_WEIGHT_INDEX; i <= FONT_SIZE_INDEX; i++) |
| 2227 | prefer_prop[i] = AREF (prefer, i); | 2194 | prefer_prop[i] = AREF (prefer, i); |
| 2228 | 2195 | ||
| 2229 | if (! NILP (spec)) | 2196 | if (! NILP (spec)) |
| @@ -2234,7 +2201,7 @@ font_sort_entites (vec, prefer, frame, spec, best_only) | |||
| 2234 | generic family name as "serif" is specified. So, to ignore | 2201 | generic family name as "serif" is specified. So, to ignore |
| 2235 | such a difference, for all properties specified in SPEC, set | 2202 | such a difference, for all properties specified in SPEC, set |
| 2236 | the corresponding properties in PREFER_PROP to nil. */ | 2203 | the corresponding properties in PREFER_PROP to nil. */ |
| 2237 | for (i = FONT_FOUNDRY_INDEX; i <= FONT_REGISTRY_INDEX; i++) | 2204 | for (i = FONT_WEIGHT_INDEX; i <= FONT_SIZE_INDEX; i++) |
| 2238 | if (! NILP (AREF (spec, i))) | 2205 | if (! NILP (AREF (spec, i))) |
| 2239 | prefer_prop[i] = Qnil; | 2206 | prefer_prop[i] = Qnil; |
| 2240 | } | 2207 | } |
| @@ -2242,24 +2209,28 @@ font_sort_entites (vec, prefer, frame, spec, best_only) | |||
| 2242 | if (FLOATP (prefer_prop[FONT_SIZE_INDEX])) | 2209 | if (FLOATP (prefer_prop[FONT_SIZE_INDEX])) |
| 2243 | prefer_prop[FONT_SIZE_INDEX] | 2210 | prefer_prop[FONT_SIZE_INDEX] |
| 2244 | = make_number (font_pixel_size (XFRAME (frame), prefer)); | 2211 | = make_number (font_pixel_size (XFRAME (frame), prefer)); |
| 2245 | if (! NILP (prefer_prop[FONT_FAMILY_INDEX])) | ||
| 2246 | { | ||
| 2247 | alternate_families | ||
| 2248 | = Fassoc_string (prefer_prop[FONT_FAMILY_INDEX], | ||
| 2249 | Vface_alternative_font_family_alist, Qt); | ||
| 2250 | if (CONSP (alternate_families)) | ||
| 2251 | alternate_families = XCDR (alternate_families); | ||
| 2252 | } | ||
| 2253 | 2212 | ||
| 2254 | /* Scoring and sorting. */ | 2213 | /* Scoring and sorting. */ |
| 2255 | SAFE_ALLOCA (data, struct font_sort_data *, (sizeof *data) * len); | 2214 | SAFE_ALLOCA (data, struct font_sort_data *, (sizeof *data) * len); |
| 2256 | best_score = 0xFFFFFFFF; | 2215 | best_score = 0xFFFFFFFF; |
| 2257 | best_entity = Qnil; | 2216 | /* We are sure that the length of VEC > 1. */ |
| 2217 | driver_type = AREF (AREF (vec, 0), FONT_TYPE_INDEX); | ||
| 2218 | for (driver_order = 0, list = f->font_driver_list; list; | ||
| 2219 | driver_order++, list = list->next) | ||
| 2220 | if (EQ (driver_type, list->driver->type)) | ||
| 2221 | break; | ||
| 2222 | best_entity = data[0].entity = AREF (vec, 0); | ||
| 2223 | best_score = data[0].score | ||
| 2224 | = font_score (data[0].entity, prefer_prop) | driver_order; | ||
| 2258 | for (i = 0; i < len; i++) | 2225 | for (i = 0; i < len; i++) |
| 2259 | { | 2226 | { |
| 2227 | if (!EQ (driver_type, AREF (AREF (vec, i), FONT_TYPE_INDEX))) | ||
| 2228 | for (driver_order = 0, list = f->font_driver_list; list; | ||
| 2229 | driver_order++, list = list->next) | ||
| 2230 | if (EQ (driver_type, list->driver->type)) | ||
| 2231 | break; | ||
| 2260 | data[i].entity = AREF (vec, i); | 2232 | data[i].entity = AREF (vec, i); |
| 2261 | data[i].score = font_score (data[i].entity, prefer_prop, | 2233 | data[i].score = font_score (data[i].entity, prefer_prop) | driver_order; |
| 2262 | alternate_families); | ||
| 2263 | if (best_only && best_score > data[i].score) | 2234 | if (best_only && best_score > data[i].score) |
| 2264 | { | 2235 | { |
| 2265 | best_score = data[i].score; | 2236 | best_score = data[i].score; |
| @@ -2335,7 +2306,7 @@ font_match_p (spec, entity) | |||
| 2335 | alternate_families = XCDR (alternate_families); | 2306 | alternate_families = XCDR (alternate_families); |
| 2336 | } | 2307 | } |
| 2337 | 2308 | ||
| 2338 | return (font_score (entity, prefer_prop, alternate_families) == 0); | 2309 | return (font_score (entity, prefer_prop) == 0); |
| 2339 | } | 2310 | } |
| 2340 | 2311 | ||
| 2341 | 2312 | ||
| @@ -2531,28 +2502,14 @@ font_list_entities (frame, spec) | |||
| 2531 | { | 2502 | { |
| 2532 | FRAME_PTR f = XFRAME (frame); | 2503 | FRAME_PTR f = XFRAME (frame); |
| 2533 | struct font_driver_list *driver_list = f->font_driver_list; | 2504 | struct font_driver_list *driver_list = f->font_driver_list; |
| 2534 | Lisp_Object ftype, family, alternate_familes, val; | 2505 | Lisp_Object ftype, val; |
| 2535 | Lisp_Object *vec; | 2506 | Lisp_Object *vec; |
| 2536 | int size; | 2507 | int size; |
| 2537 | int need_filtering = 0; | 2508 | int need_filtering = 0; |
| 2538 | int n_family = 1; | ||
| 2539 | int i; | 2509 | int i; |
| 2540 | 2510 | ||
| 2541 | font_assert (FONT_SPEC_P (spec)); | 2511 | font_assert (FONT_SPEC_P (spec)); |
| 2542 | 2512 | ||
| 2543 | family = AREF (spec, FONT_FAMILY_INDEX); | ||
| 2544 | if (NILP (family)) | ||
| 2545 | alternate_familes = Qnil; | ||
| 2546 | else | ||
| 2547 | { | ||
| 2548 | alternate_familes = Fassoc_string (family, | ||
| 2549 | Vface_alternative_font_family_alist, | ||
| 2550 | Qt); | ||
| 2551 | if (! NILP (alternate_familes)) | ||
| 2552 | alternate_familes = XCDR (alternate_familes); | ||
| 2553 | n_family += XINT (Flength (alternate_familes)); | ||
| 2554 | } | ||
| 2555 | |||
| 2556 | if (INTEGERP (AREF (spec, FONT_SIZE_INDEX))) | 2513 | if (INTEGERP (AREF (spec, FONT_SIZE_INDEX))) |
| 2557 | size = XINT (AREF (spec, FONT_SIZE_INDEX)); | 2514 | size = XINT (AREF (spec, FONT_SIZE_INDEX)); |
| 2558 | else if (FLOATP (AREF (spec, FONT_SIZE_INDEX))) | 2515 | else if (FLOATP (AREF (spec, FONT_SIZE_INDEX))) |
| @@ -2561,18 +2518,21 @@ font_list_entities (frame, spec) | |||
| 2561 | size = 0; | 2518 | size = 0; |
| 2562 | 2519 | ||
| 2563 | ftype = AREF (spec, FONT_TYPE_INDEX); | 2520 | ftype = AREF (spec, FONT_TYPE_INDEX); |
| 2564 | for (i = 1; i <= FONT_REGISTRY_INDEX; i++) | 2521 | for (i = FONT_FOUNDRY_INDEX; i <= FONT_REGISTRY_INDEX; i++) |
| 2565 | ASET (scratch_font_spec, i, AREF (spec, i)); | 2522 | ASET (scratch_font_spec, i, AREF (spec, i)); |
| 2566 | for (i = FONT_DPI_INDEX; i < FONT_EXTRA_INDEX; i += 2) | 2523 | for (i = FONT_WEIGHT_INDEX; i < FONT_EXTRA_INDEX; i++) |
| 2567 | { | 2524 | { |
| 2568 | ASET (scratch_font_spec, i, Qnil); | 2525 | ASET (scratch_font_spec, i, Qnil); |
| 2569 | if (! NILP (AREF (spec, i))) | 2526 | if (! NILP (AREF (spec, i))) |
| 2570 | need_filtering = 1; | 2527 | need_filtering = 1; |
| 2528 | if (i == FONT_DPI_INDEX) | ||
| 2529 | /* Skip FONT_SPACING_INDEX */ | ||
| 2530 | i++; | ||
| 2571 | } | 2531 | } |
| 2572 | ASET (scratch_font_spec, FONT_SPACING_INDEX, AREF (spec, FONT_SPACING_INDEX)); | 2532 | ASET (scratch_font_spec, FONT_SPACING_INDEX, AREF (spec, FONT_SPACING_INDEX)); |
| 2573 | ASET (scratch_font_spec, FONT_EXTRA_INDEX, AREF (spec, FONT_EXTRA_INDEX)); | 2533 | ASET (scratch_font_spec, FONT_EXTRA_INDEX, AREF (spec, FONT_EXTRA_INDEX)); |
| 2574 | 2534 | ||
| 2575 | vec = alloca (sizeof (Lisp_Object) * num_font_drivers * n_family); | 2535 | vec = alloca (sizeof (Lisp_Object) * num_font_drivers); |
| 2576 | if (! vec) | 2536 | if (! vec) |
| 2577 | return null_vector; | 2537 | return null_vector; |
| 2578 | 2538 | ||
| @@ -2581,37 +2541,24 @@ font_list_entities (frame, spec) | |||
| 2581 | && (NILP (ftype) || EQ (driver_list->driver->type, ftype))) | 2541 | && (NILP (ftype) || EQ (driver_list->driver->type, ftype))) |
| 2582 | { | 2542 | { |
| 2583 | Lisp_Object cache = font_get_cache (f, driver_list->driver); | 2543 | Lisp_Object cache = font_get_cache (f, driver_list->driver); |
| 2584 | Lisp_Object tail = alternate_familes; | ||
| 2585 | 2544 | ||
| 2586 | ASET (scratch_font_spec, FONT_TYPE_INDEX, driver_list->driver->type); | 2545 | ASET (scratch_font_spec, FONT_TYPE_INDEX, driver_list->driver->type); |
| 2587 | ASET (scratch_font_spec, FONT_FAMILY_INDEX, family); | 2546 | val = assoc_no_quit (scratch_font_spec, XCDR (cache)); |
| 2588 | while (1) | 2547 | if (CONSP (val)) |
| 2548 | val = XCDR (val); | ||
| 2549 | else | ||
| 2589 | { | 2550 | { |
| 2590 | val = assoc_no_quit (scratch_font_spec, XCDR (cache)); | 2551 | Lisp_Object copy; |
| 2591 | if (CONSP (val)) | ||
| 2592 | val = XCDR (val); | ||
| 2593 | else | ||
| 2594 | { | ||
| 2595 | Lisp_Object copy; | ||
| 2596 | 2552 | ||
| 2597 | val = driver_list->driver->list (frame, scratch_font_spec); | 2553 | val = driver_list->driver->list (frame, scratch_font_spec); |
| 2598 | copy = Fcopy_font_spec (scratch_font_spec); | 2554 | copy = Fcopy_font_spec (scratch_font_spec); |
| 2599 | ASET (copy, FONT_TYPE_INDEX, driver_list->driver->type); | 2555 | ASET (copy, FONT_TYPE_INDEX, driver_list->driver->type); |
| 2600 | XSETCDR (cache, Fcons (Fcons (copy, val), XCDR (cache))); | 2556 | XSETCDR (cache, Fcons (Fcons (copy, val), XCDR (cache))); |
| 2601 | } | ||
| 2602 | if (! NILP (val) && need_filtering) | ||
| 2603 | val = font_delete_unmatched (val, spec, size); | ||
| 2604 | if (! NILP (val)) | ||
| 2605 | { | ||
| 2606 | vec[i++] = val; | ||
| 2607 | break; | ||
| 2608 | } | ||
| 2609 | if (NILP (tail)) | ||
| 2610 | break; | ||
| 2611 | ASET (scratch_font_spec, FONT_FAMILY_INDEX, | ||
| 2612 | Fintern (XCAR (tail), Qnil)); | ||
| 2613 | tail = XCDR (tail); | ||
| 2614 | } | 2557 | } |
| 2558 | if (! NILP (val) && need_filtering) | ||
| 2559 | val = font_delete_unmatched (val, spec, size); | ||
| 2560 | if (! NILP (val)) | ||
| 2561 | vec[i++] = val; | ||
| 2615 | } | 2562 | } |
| 2616 | 2563 | ||
| 2617 | val = (i > 0 ? Fvconcat (i, vec) : null_vector); | 2564 | val = (i > 0 ? Fvconcat (i, vec) : null_vector); |
| @@ -2869,14 +2816,17 @@ font_clear_prop (attrs, prop) | |||
| 2869 | if (! FONTP (font)) | 2816 | if (! FONTP (font)) |
| 2870 | return; | 2817 | return; |
| 2871 | if (NILP (AREF (font, prop)) | 2818 | if (NILP (AREF (font, prop)) |
| 2872 | && prop != FONT_FAMILY_INDEX && prop != FONT_FAMILY_INDEX) | 2819 | && prop != FONT_FAMILY_INDEX && prop != FONT_FOUNDRY_INDEX |
| 2820 | && prop != FONT_SIZE_INDEX) | ||
| 2873 | return; | 2821 | return; |
| 2874 | font = Fcopy_font_spec (font); | 2822 | font = Fcopy_font_spec (font); |
| 2875 | ASET (font, prop, Qnil); | 2823 | ASET (font, prop, Qnil); |
| 2876 | if (prop == FONT_FAMILY_INDEX) | 2824 | if (prop == FONT_FAMILY_INDEX || prop == FONT_FOUNDRY_INDEX) |
| 2877 | { | 2825 | { |
| 2878 | ASET (font, FONT_FOUNDRY_INDEX, Qnil); | 2826 | if (prop == FONT_FAMILY_INDEX) |
| 2827 | ASET (font, FONT_FOUNDRY_INDEX, Qnil); | ||
| 2879 | ASET (font, FONT_ADSTYLE_INDEX, Qnil); | 2828 | ASET (font, FONT_ADSTYLE_INDEX, Qnil); |
| 2829 | ASET (font, FONT_REGISTRY_INDEX, Qnil); | ||
| 2880 | ASET (font, FONT_SIZE_INDEX, Qnil); | 2830 | ASET (font, FONT_SIZE_INDEX, Qnil); |
| 2881 | ASET (font, FONT_DPI_INDEX, Qnil); | 2831 | ASET (font, FONT_DPI_INDEX, Qnil); |
| 2882 | ASET (font, FONT_SPACING_INDEX, Qnil); | 2832 | ASET (font, FONT_SPACING_INDEX, Qnil); |
| @@ -2902,22 +2852,10 @@ font_update_lface (f, attrs) | |||
| 2902 | if (! FONT_SPEC_P (spec)) | 2852 | if (! FONT_SPEC_P (spec)) |
| 2903 | return; | 2853 | return; |
| 2904 | 2854 | ||
| 2905 | if (! NILP (AREF (spec, FONT_FOUNDRY_INDEX)) | 2855 | if (! NILP (AREF (spec, FONT_FOUNDRY_INDEX))) |
| 2906 | || ! NILP (AREF (spec, FONT_FAMILY_INDEX))) | 2856 | attrs[LFACE_FOUNDRY_INDEX] = SYMBOL_NAME (AREF (spec, FONT_FOUNDRY_INDEX)); |
| 2907 | { | 2857 | if (! NILP (AREF (spec, FONT_FAMILY_INDEX))) |
| 2908 | Lisp_Object family; | 2858 | attrs[LFACE_FAMILY_INDEX] = SYMBOL_NAME (AREF (spec, FONT_FAMILY_INDEX)); |
| 2909 | |||
| 2910 | if (NILP (AREF (spec, FONT_FOUNDRY_INDEX))) | ||
| 2911 | family = AREF (spec, FONT_FAMILY_INDEX); | ||
| 2912 | else if (NILP (AREF (spec, FONT_FAMILY_INDEX))) | ||
| 2913 | family = concat2 (SYMBOL_NAME (AREF (spec, FONT_FOUNDRY_INDEX)), | ||
| 2914 | build_string ("-*")); | ||
| 2915 | else | ||
| 2916 | family = concat3 (SYMBOL_NAME (AREF (spec, FONT_FOUNDRY_INDEX)), | ||
| 2917 | build_string ("-"), | ||
| 2918 | SYMBOL_NAME (AREF (spec, FONT_FAMILY_INDEX))); | ||
| 2919 | attrs[LFACE_FAMILY_INDEX] = family; | ||
| 2920 | } | ||
| 2921 | if (! NILP (AREF (spec, FONT_WEIGHT_INDEX))) | 2859 | if (! NILP (AREF (spec, FONT_WEIGHT_INDEX))) |
| 2922 | attrs[LFACE_WEIGHT_INDEX] = FONT_WEIGHT_FOR_FACE (spec); | 2860 | attrs[LFACE_WEIGHT_INDEX] = FONT_WEIGHT_FOR_FACE (spec); |
| 2923 | if (! NILP (AREF (spec, FONT_SLANT_INDEX))) | 2861 | if (! NILP (AREF (spec, FONT_SLANT_INDEX))) |
| @@ -2957,17 +2895,18 @@ font_find_for_lface (f, attrs, spec, c) | |||
| 2957 | Lisp_Object spec; | 2895 | Lisp_Object spec; |
| 2958 | int c; | 2896 | int c; |
| 2959 | { | 2897 | { |
| 2898 | Lisp_Object work; | ||
| 2960 | Lisp_Object frame, entities, val, props[FONT_REGISTRY_INDEX + 1] ; | 2899 | Lisp_Object frame, entities, val, props[FONT_REGISTRY_INDEX + 1] ; |
| 2961 | Lisp_Object size; | 2900 | Lisp_Object size, foundry[3], *family; |
| 2962 | int pixel_size; | 2901 | int pixel_size; |
| 2963 | int i, result; | 2902 | int i, j, result; |
| 2964 | 2903 | ||
| 2965 | if (c >= 0) | 2904 | if (c >= 0 && ! NILP (AREF (spec, FONT_REGISTRY_INDEX))) |
| 2966 | { | 2905 | { |
| 2967 | Lisp_Object registry = AREF (spec, FONT_REGISTRY_INDEX); | ||
| 2968 | struct charset *encoding, *repertory; | 2906 | struct charset *encoding, *repertory; |
| 2969 | 2907 | ||
| 2970 | if (font_registry_charsets (registry, &encoding, &repertory) < 0) | 2908 | if (font_registry_charsets (AREF (spec, FONT_REGISTRY_INDEX), |
| 2909 | &encoding, &repertory) < 0) | ||
| 2971 | return Qnil; | 2910 | return Qnil; |
| 2972 | if (repertory) | 2911 | if (repertory) |
| 2973 | { | 2912 | { |
| @@ -2981,6 +2920,7 @@ font_find_for_lface (f, attrs, spec, c) | |||
| 2981 | return Qnil; | 2920 | return Qnil; |
| 2982 | } | 2921 | } |
| 2983 | 2922 | ||
| 2923 | work = Fcopy_font_spec (spec); | ||
| 2984 | XSETFRAME (frame, f); | 2924 | XSETFRAME (frame, f); |
| 2985 | size = AREF (spec, FONT_SIZE_INDEX); | 2925 | size = AREF (spec, FONT_SIZE_INDEX); |
| 2986 | pixel_size = font_pixel_size (f, spec); | 2926 | pixel_size = font_pixel_size (f, spec); |
| @@ -2990,9 +2930,68 @@ font_find_for_lface (f, attrs, spec, c) | |||
| 2990 | 2930 | ||
| 2991 | pixel_size = POINT_TO_PIXEL (pt / 10, f->resy); | 2931 | pixel_size = POINT_TO_PIXEL (pt / 10, f->resy); |
| 2992 | } | 2932 | } |
| 2993 | ASET (spec, FONT_SIZE_INDEX, Qnil); | 2933 | ASET (work, FONT_SIZE_INDEX, Qnil); |
| 2994 | entities = font_list_entities (frame, spec); | 2934 | foundry[0] = AREF (work, FONT_FOUNDRY_INDEX); |
| 2995 | ASET (spec, FONT_SIZE_INDEX, size); | 2935 | if (! NILP (foundry[0])) |
| 2936 | foundry[1] = null_vector; | ||
| 2937 | else if (STRINGP (attrs[LFACE_FOUNDRY_INDEX])) | ||
| 2938 | { | ||
| 2939 | foundry[0] = font_intern_prop (SDATA (attrs[LFACE_FOUNDRY_INDEX]), | ||
| 2940 | SBYTES (attrs[LFACE_FOUNDRY_INDEX]), 1); | ||
| 2941 | foundry[1] = Qnil; | ||
| 2942 | foundry[2] = null_vector; | ||
| 2943 | } | ||
| 2944 | else | ||
| 2945 | foundry[0] = Qnil, foundry[1] = null_vector; | ||
| 2946 | |||
| 2947 | val = AREF (work, FONT_FAMILY_INDEX); | ||
| 2948 | if (NILP (val) && STRINGP (attrs[LFACE_FAMILY_INDEX])) | ||
| 2949 | val = font_intern_prop (SDATA (attrs[LFACE_FAMILY_INDEX]), | ||
| 2950 | SBYTES (attrs[LFACE_FAMILY_INDEX]), 1); | ||
| 2951 | if (NILP (val)) | ||
| 2952 | { | ||
| 2953 | family = alloca ((sizeof family[0]) * 2); | ||
| 2954 | family[0] = Qnil; | ||
| 2955 | family[1] = null_vector; /* terminator. */ | ||
| 2956 | } | ||
| 2957 | else | ||
| 2958 | { | ||
| 2959 | Lisp_Object alters | ||
| 2960 | = Fassoc_string (val, Vface_alternative_font_family_alist, Qt); | ||
| 2961 | |||
| 2962 | if (! NILP (alters)) | ||
| 2963 | { | ||
| 2964 | family = alloca ((sizeof family[0]) * (XINT (Flength (alters)) + 2)); | ||
| 2965 | for (i = 0; CONSP (alters); i++, alters = XCDR (alters)) | ||
| 2966 | family[i] = XCAR (alters); | ||
| 2967 | if (NILP (AREF (spec, FONT_FAMILY_INDEX))) | ||
| 2968 | family[i++] = Qnil; | ||
| 2969 | family[i] = null_vector; | ||
| 2970 | } | ||
| 2971 | else | ||
| 2972 | { | ||
| 2973 | family = alloca ((sizeof family[0]) * 3); | ||
| 2974 | i = 0; | ||
| 2975 | family[i++] = val; | ||
| 2976 | if (NILP (AREF (spec, FONT_FAMILY_INDEX))) | ||
| 2977 | family[i++] = Qnil; | ||
| 2978 | family[i] = null_vector; | ||
| 2979 | } | ||
| 2980 | } | ||
| 2981 | |||
| 2982 | for (j = 0; SYMBOLP (family[j]); j++) | ||
| 2983 | { | ||
| 2984 | ASET (work, FONT_FAMILY_INDEX, family[j]); | ||
| 2985 | for (i = 0; SYMBOLP (foundry[i]); i++) | ||
| 2986 | { | ||
| 2987 | ASET (work, FONT_FOUNDRY_INDEX, foundry[i]); | ||
| 2988 | entities = font_list_entities (frame, work); | ||
| 2989 | if (ASIZE (entities) > 0) | ||
| 2990 | break; | ||
| 2991 | } | ||
| 2992 | if (ASIZE (entities) > 0) | ||
| 2993 | break; | ||
| 2994 | } | ||
| 2996 | if (ASIZE (entities) == 0) | 2995 | if (ASIZE (entities) == 0) |
| 2997 | return Qnil; | 2996 | return Qnil; |
| 2998 | if (ASIZE (entities) == 1) | 2997 | if (ASIZE (entities) == 1) |
| @@ -3006,7 +3005,7 @@ font_find_for_lface (f, attrs, spec, c) | |||
| 3006 | Lisp_Object prefer = scratch_font_prefer; | 3005 | Lisp_Object prefer = scratch_font_prefer; |
| 3007 | 3006 | ||
| 3008 | for (i = 0; i < FONT_EXTRA_INDEX; i++) | 3007 | for (i = 0; i < FONT_EXTRA_INDEX; i++) |
| 3009 | ASET (prefer, i, AREF (spec, i)); | 3008 | ASET (prefer, i, AREF (work, i)); |
| 3010 | if (FONTP (attrs[LFACE_FONT_INDEX])) | 3009 | if (FONTP (attrs[LFACE_FONT_INDEX])) |
| 3011 | { | 3010 | { |
| 3012 | Lisp_Object face_font = attrs[LFACE_FONT_INDEX]; | 3011 | Lisp_Object face_font = attrs[LFACE_FONT_INDEX]; |
| @@ -3015,8 +3014,6 @@ font_find_for_lface (f, attrs, spec, c) | |||
| 3015 | if (NILP (AREF (prefer, i))) | 3014 | if (NILP (AREF (prefer, i))) |
| 3016 | ASET (prefer, i, AREF (face_font, i)); | 3015 | ASET (prefer, i, AREF (face_font, i)); |
| 3017 | } | 3016 | } |
| 3018 | if (NILP (AREF (prefer, FONT_FAMILY_INDEX))) | ||
| 3019 | font_parse_family_registry (attrs[LFACE_FAMILY_INDEX], Qnil, prefer); | ||
| 3020 | if (NILP (AREF (prefer, FONT_WEIGHT_INDEX))) | 3017 | if (NILP (AREF (prefer, FONT_WEIGHT_INDEX))) |
| 3021 | FONT_SET_STYLE (prefer, FONT_WEIGHT_INDEX, attrs[LFACE_WEIGHT_INDEX]); | 3018 | FONT_SET_STYLE (prefer, FONT_WEIGHT_INDEX, attrs[LFACE_WEIGHT_INDEX]); |
| 3022 | if (NILP (AREF (prefer, FONT_SLANT_INDEX))) | 3019 | if (NILP (AREF (prefer, FONT_SLANT_INDEX))) |
| @@ -3024,9 +3021,7 @@ font_find_for_lface (f, attrs, spec, c) | |||
| 3024 | if (NILP (AREF (prefer, FONT_WIDTH_INDEX))) | 3021 | if (NILP (AREF (prefer, FONT_WIDTH_INDEX))) |
| 3025 | FONT_SET_STYLE (prefer, FONT_WIDTH_INDEX, attrs[LFACE_SWIDTH_INDEX]); | 3022 | FONT_SET_STYLE (prefer, FONT_WIDTH_INDEX, attrs[LFACE_SWIDTH_INDEX]); |
| 3026 | ASET (prefer, FONT_SIZE_INDEX, make_number (pixel_size)); | 3023 | ASET (prefer, FONT_SIZE_INDEX, make_number (pixel_size)); |
| 3027 | ASET (spec, FONT_SIZE_INDEX, Qnil); | 3024 | entities = font_sort_entites (entities, prefer, frame, work, c < 0); |
| 3028 | entities = font_sort_entites (entities, prefer, frame, spec, c < 0); | ||
| 3029 | ASET (spec, FONT_SIZE_INDEX, size); | ||
| 3030 | } | 3025 | } |
| 3031 | if (c < 0) | 3026 | if (c < 0) |
| 3032 | return entities; | 3027 | return entities; |
| @@ -3072,7 +3067,10 @@ font_open_for_lface (f, entity, attrs, spec) | |||
| 3072 | { | 3067 | { |
| 3073 | int size; | 3068 | int size; |
| 3074 | 3069 | ||
| 3075 | if (FONT_SPEC_P (spec) && ! NILP (AREF (spec, FONT_SIZE_INDEX))) | 3070 | if (INTEGERP (AREF (entity, FONT_SIZE_INDEX)) |
| 3071 | && XINT (AREF (entity, FONT_SIZE_INDEX)) > 0) | ||
| 3072 | size = XINT (AREF (entity, FONT_SIZE_INDEX)); | ||
| 3073 | else if (FONT_SPEC_P (spec) && ! NILP (AREF (spec, FONT_SIZE_INDEX))) | ||
| 3076 | size = font_pixel_size (f, spec); | 3074 | size = font_pixel_size (f, spec); |
| 3077 | else | 3075 | else |
| 3078 | { | 3076 | { |
| @@ -3144,63 +3142,20 @@ font_open_by_name (f, name) | |||
| 3144 | char *name; | 3142 | char *name; |
| 3145 | { | 3143 | { |
| 3146 | Lisp_Object args[2]; | 3144 | Lisp_Object args[2]; |
| 3147 | Lisp_Object spec, prefer, size, registry, entity, entity_list; | 3145 | Lisp_Object spec, attrs[LFACE_VECTOR_SIZE]; |
| 3148 | Lisp_Object frame; | ||
| 3149 | int i; | ||
| 3150 | int pixel_size; | ||
| 3151 | |||
| 3152 | XSETFRAME (frame, f); | ||
| 3153 | 3146 | ||
| 3154 | args[0] = QCname; | 3147 | args[0] = QCname; |
| 3155 | args[1] = make_unibyte_string (name, strlen (name)); | 3148 | args[1] = make_unibyte_string (name, strlen (name)); |
| 3156 | spec = Ffont_spec (2, args); | 3149 | spec = Ffont_spec (2, args); |
| 3157 | prefer = scratch_font_prefer; | 3150 | /* We set up the default font-related attributes of a face to prefer |
| 3158 | for (i = 0; i < FONT_SPEC_MAX; i++) | 3151 | a moderate font. */ |
| 3159 | { | 3152 | attrs[LFACE_FAMILY_INDEX] = attrs[LFACE_FOUNDRY_INDEX] = Qnil; |
| 3160 | ASET (prefer, i, AREF (spec, i)); | 3153 | attrs[LFACE_SWIDTH_INDEX] = attrs[LFACE_WEIGHT_INDEX] |
| 3161 | if (NILP (AREF (prefer, i)) | 3154 | = attrs[LFACE_SLANT_INDEX] = Qnormal; |
| 3162 | && i >= FONT_WEIGHT_INDEX && i <= FONT_WIDTH_INDEX) | 3155 | attrs[LFACE_HEIGHT_INDEX] = make_number (120); |
| 3163 | FONT_SET_STYLE (prefer, i, make_number (100)); | 3156 | attrs[LFACE_FONT_INDEX] = Qnil; |
| 3164 | } | 3157 | |
| 3165 | size = AREF (spec, FONT_SIZE_INDEX); | 3158 | return font_load_for_lface (f, attrs, spec); |
| 3166 | if (NILP (size)) | ||
| 3167 | pixel_size = 0; | ||
| 3168 | else | ||
| 3169 | { | ||
| 3170 | if (INTEGERP (size)) | ||
| 3171 | pixel_size = XINT (size); | ||
| 3172 | else /* FLOATP (size) */ | ||
| 3173 | { | ||
| 3174 | double pt = XFLOAT_DATA (size); | ||
| 3175 | |||
| 3176 | pixel_size = POINT_TO_PIXEL (pt, f->resy); | ||
| 3177 | } | ||
| 3178 | if (pixel_size == 0) | ||
| 3179 | ASET (spec, FONT_SIZE_INDEX, Qnil); | ||
| 3180 | } | ||
| 3181 | if (pixel_size == 0) | ||
| 3182 | { | ||
| 3183 | pixel_size = POINT_TO_PIXEL (12.0, f->resy); | ||
| 3184 | size = make_number (pixel_size); | ||
| 3185 | ASET (prefer, FONT_SIZE_INDEX, size); | ||
| 3186 | } | ||
| 3187 | registry = AREF (spec, FONT_REGISTRY_INDEX); | ||
| 3188 | if (NILP (registry)) | ||
| 3189 | ASET (spec, FONT_REGISTRY_INDEX, Qiso8859_1); | ||
| 3190 | entity_list = Flist_fonts (spec, frame, make_number (1), prefer); | ||
| 3191 | if (NILP (entity_list) && NILP (registry)) | ||
| 3192 | { | ||
| 3193 | ASET (spec, FONT_REGISTRY_INDEX, Qascii_0); | ||
| 3194 | entity_list = Flist_fonts (spec, frame, make_number (1), prefer); | ||
| 3195 | } | ||
| 3196 | ASET (spec, FONT_REGISTRY_INDEX, registry); | ||
| 3197 | if (NILP (entity_list)) | ||
| 3198 | entity = font_matching_entity (f, NULL, spec); | ||
| 3199 | else | ||
| 3200 | entity = XCAR (entity_list); | ||
| 3201 | return (NILP (entity) | ||
| 3202 | ? Qnil | ||
| 3203 | : font_open_entity (f, entity, pixel_size)); | ||
| 3204 | } | 3159 | } |
| 3205 | 3160 | ||
| 3206 | 3161 | ||
| @@ -3247,23 +3202,6 @@ register_font_driver (driver, f) | |||
| 3247 | } | 3202 | } |
| 3248 | 3203 | ||
| 3249 | 3204 | ||
| 3250 | /* Free font-driver list on frame F. It doesn't free font-drivers | ||
| 3251 | themselves. */ | ||
| 3252 | |||
| 3253 | void | ||
| 3254 | free_font_driver_list (f) | ||
| 3255 | FRAME_PTR f; | ||
| 3256 | { | ||
| 3257 | while (f->font_driver_list) | ||
| 3258 | { | ||
| 3259 | struct font_driver_list *next = f->font_driver_list->next; | ||
| 3260 | |||
| 3261 | free (f->font_driver_list); | ||
| 3262 | f->font_driver_list = next; | ||
| 3263 | } | ||
| 3264 | } | ||
| 3265 | |||
| 3266 | |||
| 3267 | /* Make the frame F use font backends listed in NEW_DRIVERS (list of | 3205 | /* Make the frame F use font backends listed in NEW_DRIVERS (list of |
| 3268 | symbols, e.g. xft, x). If NEW_DRIVERS is t, make F use all | 3206 | symbols, e.g. xft, x). If NEW_DRIVERS is t, make F use all |
| 3269 | available font drivers. If NEW_DRIVERS is nil, finalize all drivers. | 3207 | available font drivers. If NEW_DRIVERS is nil, finalize all drivers. |
| @@ -3278,36 +3216,75 @@ font_update_drivers (f, new_drivers) | |||
| 3278 | Lisp_Object new_drivers; | 3216 | Lisp_Object new_drivers; |
| 3279 | { | 3217 | { |
| 3280 | Lisp_Object active_drivers = Qnil; | 3218 | Lisp_Object active_drivers = Qnil; |
| 3219 | struct font_driver *driver; | ||
| 3281 | struct font_driver_list *list; | 3220 | struct font_driver_list *list; |
| 3282 | 3221 | ||
| 3222 | /* At first, turn off non-requested drivers, and turn on requested | ||
| 3223 | drivers. */ | ||
| 3283 | for (list = f->font_driver_list; list; list = list->next) | 3224 | for (list = f->font_driver_list; list; list = list->next) |
| 3284 | if (list->on) | 3225 | { |
| 3285 | { | 3226 | driver = list->driver; |
| 3286 | if (! EQ (new_drivers, Qt) | 3227 | if ((EQ (new_drivers, Qt) || ! NILP (Fmemq (driver->type, new_drivers))) |
| 3287 | && NILP (Fmemq (list->driver->type, new_drivers))) | 3228 | != list->on) |
| 3288 | { | 3229 | { |
| 3289 | if (list->driver->end_for_frame) | 3230 | if (list->on) |
| 3290 | list->driver->end_for_frame (f); | 3231 | { |
| 3291 | font_finish_cache (f, list->driver); | 3232 | if (driver->end_for_frame) |
| 3292 | list->on = 0; | 3233 | driver->end_for_frame (f); |
| 3293 | } | 3234 | font_finish_cache (f, driver); |
| 3294 | } | 3235 | list->on = 0; |
| 3295 | else | 3236 | } |
| 3296 | { | 3237 | else |
| 3297 | if (EQ (new_drivers, Qt) | 3238 | { |
| 3298 | || ! NILP (Fmemq (list->driver->type, new_drivers))) | 3239 | if (! driver->start_for_frame |
| 3299 | { | 3240 | || driver->start_for_frame (f) == 0) |
| 3300 | if (! list->driver->start_for_frame | 3241 | { |
| 3301 | || list->driver->start_for_frame (f) == 0) | 3242 | font_prepare_cache (f, driver); |
| 3302 | { | 3243 | list->on = 1; |
| 3303 | font_prepare_cache (f, list->driver); | 3244 | } |
| 3304 | list->on = 1; | 3245 | } |
| 3305 | active_drivers = nconc2 (active_drivers, | 3246 | } |
| 3306 | Fcons (list->driver->type, Qnil)); | 3247 | } |
| 3307 | } | 3248 | |
| 3308 | } | 3249 | if (NILP (new_drivers)) |
| 3309 | } | 3250 | return Qnil; |
| 3251 | |||
| 3252 | if (! EQ (new_drivers, Qt)) | ||
| 3253 | { | ||
| 3254 | /* Re-order the driver list according to new_drivers. */ | ||
| 3255 | struct font_driver_list **list_table, *list; | ||
| 3256 | Lisp_Object tail; | ||
| 3257 | int i; | ||
| 3258 | |||
| 3259 | list_table = alloca (sizeof list_table[0] * (num_font_drivers + 1)); | ||
| 3260 | for (i = 0, tail = new_drivers; ! NILP (tail); tail = XCDR (tail)) | ||
| 3261 | { | ||
| 3262 | for (list = f->font_driver_list; list; list = list->next) | ||
| 3263 | if (list->on && EQ (list->driver->type, XCAR (tail))) | ||
| 3264 | break; | ||
| 3265 | if (list) | ||
| 3266 | list_table[i++] = list; | ||
| 3267 | } | ||
| 3268 | for (list = f->font_driver_list; list; list = list->next) | ||
| 3269 | if (! list->on) | ||
| 3270 | list_table[i] = list; | ||
| 3271 | list_table[i] = NULL; | ||
| 3272 | |||
| 3273 | f->font_driver_list = list = NULL; | ||
| 3274 | for (i = 0; list_table[i]; i++) | ||
| 3275 | { | ||
| 3276 | if (list) | ||
| 3277 | list->next = list_table[i], list = list->next; | ||
| 3278 | else | ||
| 3279 | f->font_driver_list = list = list_table[i]; | ||
| 3280 | } | ||
| 3281 | list->next = NULL; | ||
| 3282 | } | ||
| 3310 | 3283 | ||
| 3284 | for (list = f->font_driver_list; list; list = list->next) | ||
| 3285 | if (list->on) | ||
| 3286 | active_drivers = nconc2 (active_drivers, | ||
| 3287 | Fcons (list->driver->type, Qnil)); | ||
| 3311 | return active_drivers; | 3288 | return active_drivers; |
| 3312 | } | 3289 | } |
| 3313 | 3290 | ||
| @@ -4646,15 +4623,12 @@ extern void syms_of_atmfont P_ (()); | |||
| 4646 | void | 4623 | void |
| 4647 | syms_of_font () | 4624 | syms_of_font () |
| 4648 | { | 4625 | { |
| 4649 | sort_shift_bits[FONT_SLANT_INDEX] = 0; | 4626 | sort_shift_bits[FONT_TYPE_INDEX] = 0; |
| 4650 | sort_shift_bits[FONT_WEIGHT_INDEX] = 7; | 4627 | sort_shift_bits[FONT_SLANT_INDEX] = 2; |
| 4651 | sort_shift_bits[FONT_SIZE_INDEX] = 14; | 4628 | sort_shift_bits[FONT_WEIGHT_INDEX] = 9; |
| 4652 | sort_shift_bits[FONT_WIDTH_INDEX] = 21; | 4629 | sort_shift_bits[FONT_SIZE_INDEX] = 16; |
| 4653 | sort_shift_bits[FONT_ADSTYLE_INDEX] = 28; | 4630 | sort_shift_bits[FONT_WIDTH_INDEX] = 23; |
| 4654 | sort_shift_bits[FONT_FOUNDRY_INDEX] = 29; | 4631 | /* Note that the other elements in sort_shift_bits are not used. */ |
| 4655 | sort_shift_bits[FONT_FAMILY_INDEX] = 30; | ||
| 4656 | /* Note that sort_shift_bits[FONT_SORT_TYPE] and | ||
| 4657 | sort_shift_bits[FONT_SORT_REGISTRY] are never used. */ | ||
| 4658 | 4632 | ||
| 4659 | staticpro (&font_charset_alist); | 4633 | staticpro (&font_charset_alist); |
| 4660 | font_charset_alist = Qnil; | 4634 | font_charset_alist = Qnil; |