1 /* GDK - The GIMP Drawing Kit
2 * Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball and Josh MacDonald
3 * Copyright (C) 1998-2002 Tor Lillqvist
5 * This library is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU Lesser General Public
7 * License as published by the Free Software Foundation; either
8 * version 2 of the License, or (at your option) any later version.
10 * This library is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * Lesser General Public License for more details.
15 * You should have received a copy of the GNU Lesser General Public
16 * License along with this library; if not, write to the
17 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18 * Boston, MA 02111-1307, USA.
22 * Modified by the GTK+ Team and others 1997-2000. See the AUTHORS
23 * file for a list of people on the GTK+ Team. See the ChangeLog
24 * files for a list of changes. These files are distributed with
25 * GTK+ at ftp://ftp.gtk.org/pub/gtk/.
34 #include "gdkpango.h" /* gdk_pango_context_get() */
35 #include "gdkdisplay.h"
36 #include "gdkprivate-win32.h"
38 static GHashTable *font_name_hash = NULL;
39 static GHashTable *fontset_name_hash = NULL;
42 gdk_font_hash_insert (GdkFontType type,
44 const gchar *font_name)
46 GdkFontPrivateWin32 *private = (GdkFontPrivateWin32 *) font;
47 GHashTable **hashp = (type == GDK_FONT_FONT) ?
48 &font_name_hash : &fontset_name_hash;
51 *hashp = g_hash_table_new (g_str_hash, g_str_equal);
53 private->names = g_slist_prepend (private->names, g_strdup (font_name));
54 g_hash_table_insert (*hashp, private->names->data, font);
58 gdk_font_hash_remove (GdkFontType type,
61 GdkFontPrivateWin32 *private = (GdkFontPrivateWin32 *) font;
63 GHashTable *hash = (type == GDK_FONT_FONT) ?
64 font_name_hash : fontset_name_hash;
66 tmp_list = private->names;
69 g_hash_table_remove (hash, tmp_list->data);
70 g_free (tmp_list->data);
72 tmp_list = tmp_list->next;
75 g_slist_free (private->names);
76 private->names = NULL;
80 gdk_font_hash_lookup (GdkFontType type,
81 const gchar *font_name)
84 GHashTable *hash = (type == GDK_FONT_FONT) ?
85 font_name_hash : fontset_name_hash;
91 result = g_hash_table_lookup (hash, font_name);
93 gdk_font_ref (result);
100 charset_name (DWORD charset)
104 case ANSI_CHARSET: return "ansi";
105 case DEFAULT_CHARSET: return "default";
106 case SYMBOL_CHARSET: return "symbol";
107 case SHIFTJIS_CHARSET: return "shiftjis";
108 case HANGEUL_CHARSET: return "hangeul";
109 case GB2312_CHARSET: return "gb2312";
110 case CHINESEBIG5_CHARSET: return "big5";
111 case JOHAB_CHARSET: return "johab";
112 case HEBREW_CHARSET: return "hebrew";
113 case ARABIC_CHARSET: return "arabic";
114 case GREEK_CHARSET: return "greek";
115 case TURKISH_CHARSET: return "turkish";
116 case VIETNAMESE_CHARSET: return "vietnamese";
117 case THAI_CHARSET: return "thai";
118 case EASTEUROPE_CHARSET: return "easteurope";
119 case RUSSIAN_CHARSET: return "russian";
120 case MAC_CHARSET: return "mac";
121 case BALTIC_CHARSET: return "baltic";
126 /* This table classifies Unicode characters according to the Microsoft
127 * Unicode subset numbering. This is based on the table in "Developing
128 * International Software for Windows 95 and Windows NT". This is almost,
129 * but not quite, the same as the official Unicode block table in
130 * Blocks.txt from ftp.unicode.org. The bit number field is the bitfield
131 * number as in the FONTSIGNATURE struct's fsUsb field.
132 * There are some grave bugs in the table in the books. For instance
133 * it claims there are Hangul at U+3400..U+4DFF while this range in
134 * fact contains CJK Unified Ideographs Extension A. Also, the whole
135 * block of Hangul Syllables U+AC00..U+D7A3 is missing from the book.
141 U_LATIN_1_SUPPLEMENT = 1,
142 U_LATIN_EXTENDED_A = 2,
143 U_LATIN_EXTENDED_B = 3,
144 U_IPA_EXTENSIONS = 4,
145 U_SPACING_MODIFIER_LETTERS = 5,
146 U_COMBINING_DIACRITICAL_MARKS = 6,
148 U_GREEK_SYMBOLS_AND_COPTIC = 8,
151 U_HEBREW_EXTENDED = 12,
154 U_ARABIC_EXTENDED = 14,
166 U_GEORGIAN_EXTENDED = 27,
167 U_BASIC_GEORGIAN = 26,
169 U_LATIN_EXTENDED_ADDITIONAL = 29,
170 U_GREEK_EXTENDED = 30,
171 U_GENERAL_PUNCTUATION = 31,
172 U_SUPERSCRIPTS_AND_SUBSCRIPTS = 32,
173 U_CURRENCY_SYMBOLS = 33,
174 U_COMBINING_DIACRITICAL_MARKS_FOR_SYMBOLS = 34,
175 U_LETTERLIKE_SYMBOLS = 35,
178 U_MATHEMATICAL_OPERATORS = 38,
179 U_MISCELLANEOUS_TECHNICAL = 39,
180 U_CONTROL_PICTURES = 40,
181 U_OPTICAL_CHARACTER_RECOGNITION = 41,
182 U_ENCLOSED_ALPHANUMERICS = 42,
184 U_BLOCK_ELEMENTS = 44,
185 U_GEOMETRIC_SHAPES = 45,
186 U_MISCELLANEOUS_SYMBOLS = 46,
188 U_CJK_SYMBOLS_AND_PUNCTUATION = 48,
192 U_HANGUL_COMPATIBILITY_JAMO = 52,
193 U_CJK_MISCELLANEOUS = 53,
195 U_CJK_COMPATIBILITY = 55,
197 U_HANGUL_SUPPLEMENTARY_A = 57,
198 U_HANGUL_SUPPLEMENTARY_B = 58,
199 U_CJK_UNIFIED_IDEOGRAPHS = 59,
200 U_PRIVATE_USE_AREA = 60,
201 U_CJK_COMPATIBILITY_IDEOGRAPHS = 61,
202 U_ALPHABETIC_PRESENTATION_FORMS = 62,
203 U_ARABIC_PRESENTATION_FORMS_A = 63,
204 U_COMBINING_HALF_MARKS = 64,
205 U_CJK_COMPATIBILITY_FORMS = 65,
206 U_SMALL_FORM_VARIANTS = 66,
207 U_ARABIC_PRESENTATION_FORMS_B = 67,
209 U_HALFWIDTH_AND_FULLWIDTH_FORMS = 68,
220 U_BASIC_LATIN, "Basic Latin" },
222 U_LATIN_1_SUPPLEMENT, "Latin-1 Supplement" },
224 U_LATIN_EXTENDED_A, "Latin Extended-A" },
226 U_LATIN_EXTENDED_B, "Latin Extended-B" },
228 U_IPA_EXTENSIONS, "IPA Extensions" },
230 U_SPACING_MODIFIER_LETTERS, "Spacing Modifier Letters" },
232 U_COMBINING_DIACRITICAL_MARKS, "Combining Diacritical Marks" },
234 U_BASIC_GREEK, "Basic Greek" },
236 U_GREEK_SYMBOLS_AND_COPTIC, "Greek Symbols and Coptic" },
238 U_CYRILLIC, "Cyrillic" },
240 U_ARMENIAN, "Armenian" },
242 U_HEBREW_EXTENDED, "Hebrew Extended" },
244 U_BASIC_HEBREW, "Basic Hebrew" },
246 U_BASIC_ARABIC, "Basic Arabic" },
248 U_ARABIC_EXTENDED, "Arabic Extended" },
250 U_DEVANAGARI, "Devanagari" },
252 U_BENGALI, "Bengali" },
254 U_GURMUKHI, "Gurmukhi" },
256 U_GUJARATI, "Gujarati" },
262 U_TELUGU, "Telugu" },
264 U_KANNADA, "Kannada" },
266 U_MALAYALAM, "Malayalam" },
272 U_GEORGIAN_EXTENDED, "Georgian Extended" },
274 U_BASIC_GEORGIAN, "Basic Georgian" },
276 U_HANGUL_JAMO, "Hangul Jamo" },
278 U_LATIN_EXTENDED_ADDITIONAL, "Latin Extended Additional" },
280 U_GREEK_EXTENDED, "Greek Extended" },
282 U_GENERAL_PUNCTUATION, "General Punctuation" },
284 U_SUPERSCRIPTS_AND_SUBSCRIPTS, "Superscripts and Subscripts" },
286 U_CURRENCY_SYMBOLS, "Currency Symbols" },
288 U_COMBINING_DIACRITICAL_MARKS_FOR_SYMBOLS, "Combining Diacritical Marks for Symbols" },
290 U_LETTERLIKE_SYMBOLS, "Letterlike Symbols" },
292 U_NUMBER_FORMS, "Number Forms" },
294 U_ARROWS, "Arrows" },
296 U_MATHEMATICAL_OPERATORS, "Mathematical Operators" },
298 U_MISCELLANEOUS_TECHNICAL, "Miscellaneous Technical" },
300 U_CONTROL_PICTURES, "Control Pictures" },
302 U_OPTICAL_CHARACTER_RECOGNITION, "Optical Character Recognition" },
304 U_ENCLOSED_ALPHANUMERICS, "Enclosed Alphanumerics" },
306 U_BOX_DRAWING, "Box Drawing" },
308 U_BLOCK_ELEMENTS, "Block Elements" },
310 U_GEOMETRIC_SHAPES, "Geometric Shapes" },
312 U_MISCELLANEOUS_SYMBOLS, "Miscellaneous Symbols" },
314 U_DINGBATS, "Dingbats" },
316 U_CJK_SYMBOLS_AND_PUNCTUATION, "CJK Symbols and Punctuation" },
318 U_HIRAGANA, "Hiragana" },
320 U_KATAKANA, "Katakana" },
322 U_BOPOMOFO, "Bopomofo" },
324 U_HANGUL_COMPATIBILITY_JAMO, "Hangul Compatibility Jamo" },
326 U_CJK_MISCELLANEOUS, "CJK Miscellaneous" },
328 U_ENCLOSED_CJK, "Enclosed CJK" },
330 U_CJK_COMPATIBILITY, "CJK Compatibility" },
332 * U+3400..U+3D2D = Hangul
333 * U+3D2E..U+44B7 = Hangul Supplementary A
334 * U+44B8..U+4DFF = Hangul Supplementary B
335 * but actually in Unicode
336 * U+3400..U+4DB5 = CJK Unified Ideographs Extension A
339 U_CJK_UNIFIED_IDEOGRAPHS, "CJK Unified Ideographs Extension A" },
341 U_CJK_UNIFIED_IDEOGRAPHS, "CJK Unified Ideographs" },
342 /* This was missing completely from the book's table. */
344 U_HANGUL, "Hangul Syllables" },
346 U_PRIVATE_USE_AREA, "Private Use Area" },
348 U_CJK_COMPATIBILITY_IDEOGRAPHS, "CJK Compatibility Ideographs" },
350 U_ALPHABETIC_PRESENTATION_FORMS, "Alphabetic Presentation Forms" },
352 U_ARABIC_PRESENTATION_FORMS_A, "Arabic Presentation Forms-A" },
354 U_COMBINING_HALF_MARKS, "Combining Half Marks" },
356 U_CJK_COMPATIBILITY_FORMS, "CJK Compatibility Forms" },
358 U_SMALL_FORM_VARIANTS, "Small Form Variants" },
360 U_ARABIC_PRESENTATION_FORMS_B, "Arabic Presentation Forms-B" },
362 U_SPECIALS, "Specials" },
364 U_HALFWIDTH_AND_FULLWIDTH_FORMS, "Halfwidth and Fullwidth Forms" },
366 U_SPECIALS, "Specials" }
370 print_unicode_subranges (FONTSIGNATURE *fsp)
373 gboolean checked[G_N_ELEMENTS (utab)];
374 gboolean need_comma = FALSE;
376 memset (checked, 0, sizeof (checked));
378 for (i = 0; i < G_N_ELEMENTS (utab); i++)
380 && (fsp->fsUsb[utab[i].bit/32] & (1 << (utab[i].bit % 32))))
382 g_print ("%s %s", (need_comma ? "," : ""), utab[i].name);
392 check_unicode_subranges (UINT charset,
396 gboolean retval = FALSE;
398 /* If the fsUsb bit array has at least one of the bits set, trust it */
399 for (i = 0; i < U_LAST_PLUS_ONE; i++)
400 if (i != U_PRIVATE_USE_AREA && (fsp->fsUsb[i/32] & (1 << (i % 32))))
403 /* Otherwise, guess what subranges there should be in the font */
404 fsp->fsUsb[0] = fsp->fsUsb[1] = fsp->fsUsb[2] = fsp->fsUsb[3] = 0;
406 #define set_bit(bitno) (fsp->fsUsb[(bitno)/32] |= (1 << ((bitno) % 32)))
408 /* Set Unicode subrange bits based on code pages supported.
409 * This is mostly just guesswork.
412 #define check_cp(bit) (fsp->fsCsb[0] & (bit))
414 if (check_cp(FS_LATIN1))
416 set_bit (U_BASIC_LATIN);
417 set_bit (U_LATIN_1_SUPPLEMENT);
418 set_bit (U_CURRENCY_SYMBOLS);
421 if (check_cp (FS_LATIN2))
423 set_bit (U_BASIC_LATIN);
424 set_bit (U_LATIN_1_SUPPLEMENT);
425 set_bit (U_LATIN_EXTENDED_A);
426 set_bit (U_CURRENCY_SYMBOLS);
429 if (check_cp (FS_CYRILLIC))
431 set_bit (U_BASIC_LATIN);
432 set_bit (U_CYRILLIC);
435 if (check_cp (FS_GREEK))
437 set_bit (U_BASIC_LATIN);
438 set_bit (U_BASIC_GREEK);
441 if (check_cp (FS_TURKISH))
443 set_bit (U_BASIC_LATIN);
444 set_bit (U_LATIN_1_SUPPLEMENT);
445 set_bit (U_LATIN_EXTENDED_A);
446 set_bit (U_CURRENCY_SYMBOLS);
449 if (check_cp (FS_HEBREW))
451 set_bit (U_BASIC_LATIN);
452 set_bit (U_CURRENCY_SYMBOLS);
453 set_bit (U_BASIC_HEBREW);
454 set_bit (U_HEBREW_EXTENDED);
457 if (check_cp (FS_ARABIC))
459 set_bit (U_BASIC_LATIN);
460 set_bit (U_CURRENCY_SYMBOLS);
461 set_bit (U_BASIC_ARABIC);
462 set_bit (U_ARABIC_EXTENDED);
465 if (check_cp (FS_BALTIC))
467 set_bit (U_BASIC_LATIN);
468 set_bit (U_LATIN_1_SUPPLEMENT);
469 set_bit (U_CURRENCY_SYMBOLS);
470 set_bit (U_LATIN_EXTENDED_A);
471 set_bit (U_LATIN_EXTENDED_B);
474 if (check_cp (FS_VIETNAMESE))
477 set_bit (U_BASIC_LATIN);
480 if (check_cp (FS_THAI))
482 set_bit (U_BASIC_LATIN);
486 if (check_cp (FS_JISJAPAN))
488 /* Based on MS Gothic */
489 set_bit (U_BASIC_LATIN);
490 set_bit (U_CJK_SYMBOLS_AND_PUNCTUATION);
491 set_bit (U_HIRAGANA);
492 set_bit (U_KATAKANA);
493 set_bit (U_CJK_UNIFIED_IDEOGRAPHS);
494 set_bit (U_HALFWIDTH_AND_FULLWIDTH_FORMS);
497 if (check_cp (FS_CHINESESIMP))
499 /* Based on MS Hei */
500 set_bit (U_BASIC_LATIN);
501 set_bit (U_HIRAGANA);
502 set_bit (U_KATAKANA);
503 set_bit (U_BOPOMOFO);
504 set_bit (U_CJK_UNIFIED_IDEOGRAPHS);
507 if (check_cp (FS_WANSUNG)
508 || check_cp (FS_JOHAB)) /* ??? */
510 /* Based on GulimChe. I wonder if all Korean fonts
511 * really support this large range of Unicode subranges?
513 set_bit (U_BASIC_LATIN);
514 set_bit (U_LATIN_1_SUPPLEMENT);
515 set_bit (U_LATIN_EXTENDED_A);
516 set_bit (U_SPACING_MODIFIER_LETTERS);
517 set_bit (U_BASIC_GREEK);
518 set_bit (U_CYRILLIC);
519 set_bit (U_HANGUL_JAMO);
520 set_bit (U_GENERAL_PUNCTUATION);
521 set_bit (U_SUPERSCRIPTS_AND_SUBSCRIPTS);
522 set_bit (U_CURRENCY_SYMBOLS);
523 set_bit (U_LETTERLIKE_SYMBOLS);
524 set_bit (U_NUMBER_FORMS);
526 set_bit (U_MATHEMATICAL_OPERATORS);
527 set_bit (U_MISCELLANEOUS_TECHNICAL);
528 set_bit (U_ENCLOSED_ALPHANUMERICS);
529 set_bit (U_BOX_DRAWING);
530 set_bit (U_BLOCK_ELEMENTS);
531 set_bit (U_GEOMETRIC_SHAPES);
532 set_bit (U_MISCELLANEOUS_SYMBOLS);
533 set_bit (U_CJK_SYMBOLS_AND_PUNCTUATION);
534 set_bit (U_HIRAGANA);
535 set_bit (U_KATAKANA);
536 set_bit (U_HANGUL_COMPATIBILITY_JAMO);
537 set_bit (U_ENCLOSED_CJK);
538 set_bit (U_CJK_COMPATIBILITY_FORMS);
540 set_bit (U_CJK_UNIFIED_IDEOGRAPHS);
541 set_bit (U_CJK_COMPATIBILITY_IDEOGRAPHS);
542 set_bit (U_HALFWIDTH_AND_FULLWIDTH_FORMS);
545 if (check_cp (FS_CHINESETRAD))
547 /* Based on MingLiU */
548 set_bit (U_BASIC_LATIN);
549 set_bit (U_GENERAL_PUNCTUATION);
550 set_bit (U_BOX_DRAWING);
551 set_bit (U_BLOCK_ELEMENTS);
552 set_bit (U_CJK_SYMBOLS_AND_PUNCTUATION);
553 set_bit (U_BOPOMOFO);
554 set_bit (U_CJK_UNIFIED_IDEOGRAPHS);
555 set_bit (U_CJK_COMPATIBILITY_IDEOGRAPHS);
556 set_bit (U_SMALL_FORM_VARIANTS);
557 set_bit (U_HALFWIDTH_AND_FULLWIDTH_FORMS);
560 if (check_cp (FS_SYMBOL) || charset == MAC_CHARSET)
562 /* Non-Unicode encoding, I guess. Pretend it covers
563 * the single-byte range of values.
565 set_bit (U_BASIC_LATIN);
566 set_bit (U_LATIN_1_SUPPLEMENT);
573 GDK_NOTE (MISC, g_print ("... No code page bits set!\n"));
575 /* Sigh. Not even any code page bits were set. Guess based on
576 * charset, then. These somewhat optimistic guesses are based on the
577 * table in Appendix M in the book "Developing ..." mentioned
583 set_bit (U_BASIC_LATIN);
584 set_bit (U_LATIN_1_SUPPLEMENT);
585 set_bit (U_LATIN_EXTENDED_A);
586 set_bit (U_LATIN_EXTENDED_B);
587 set_bit (U_SPACING_MODIFIER_LETTERS);
588 set_bit (U_COMBINING_DIACRITICAL_MARKS);
589 set_bit (U_GENERAL_PUNCTUATION);
590 set_bit (U_SUPERSCRIPTS_AND_SUBSCRIPTS);
591 set_bit (U_CURRENCY_SYMBOLS);
592 #if 0 /* I find this too hard to believe... */
593 set_bit (U_BASIC_GREEK);
594 set_bit (U_CYRILLIC);
595 set_bit (U_BASIC_HEBREW);
596 set_bit (U_HEBREW_EXTENDED);
597 set_bit (U_BASIC_ARABIC);
598 set_bit (U_ARABIC_EXTENDED);
599 set_bit (U_LETTERLIKE_SYMBOLS);
600 set_bit (U_NUMBER_FORMS);
602 set_bit (U_MATHEMATICAL_OPERATORS);
603 set_bit (U_MISCELLANEOUS_TECHNICAL);
604 set_bit (U_ENCLOSED_ALPHANUMERICS);
605 set_bit (U_BOX_DRAWING);
606 set_bit (U_BLOCK_ELEMENTS);
607 set_bit (U_GEOMETRIC_SHAPES);
608 set_bit (U_MISCELLANEOUS_SYMBOLS);
609 set_bit (U_HIRAGANA);
610 set_bit (U_KATAKANA);
611 set_bit (U_BOPOMOFO);
612 set_bit (U_HANGUL_COMPATIBILITY_JAMO);
613 set_bit (U_CJK_MISCELLANEOUS);
614 set_bit (U_CJK_COMPATIBILITY);
616 set_bit (U_HANGUL_SUPPLEMENTARY_A);
617 set_bit (U_CJK_COMPATIBILITY_IDEOGRAPHS);
618 set_bit (U_ALPHABETIC_PRESENTATION_FORMS);
619 set_bit (U_SMALL_FORM_VARIANTS);
620 set_bit (U_ARABIC_PRESENTATION_FORMS_B);
621 set_bit (U_HALFWIDTH_AND_FULLWIDTH_FORMS);
622 set_bit (U_SPECIALS);
628 set_bit (U_BASIC_LATIN);
629 set_bit (U_LATIN_1_SUPPLEMENT);
632 case SHIFTJIS_CHARSET:
633 case HANGEUL_CHARSET:
635 case CHINESEBIG5_CHARSET:
637 /* The table really does claim these "locales" (it doesn't
638 * talk about charsets per se) cover the same Unicode
641 set_bit (U_BASIC_LATIN);
642 set_bit (U_LATIN_1_SUPPLEMENT);
643 set_bit (U_LATIN_EXTENDED_A);
644 set_bit (U_LATIN_EXTENDED_B);
645 set_bit (U_SPACING_MODIFIER_LETTERS);
646 set_bit (U_COMBINING_DIACRITICAL_MARKS_FOR_SYMBOLS);
647 set_bit (U_BASIC_GREEK);
648 set_bit (U_CYRILLIC);
649 set_bit (U_HANGUL_JAMO);
650 set_bit (U_GENERAL_PUNCTUATION);
651 set_bit (U_SUPERSCRIPTS_AND_SUBSCRIPTS);
652 set_bit (U_CURRENCY_SYMBOLS);
653 set_bit (U_LETTERLIKE_SYMBOLS);
654 set_bit (U_NUMBER_FORMS);
656 set_bit (U_MATHEMATICAL_OPERATORS);
657 set_bit (U_MISCELLANEOUS_TECHNICAL);
658 set_bit (U_ENCLOSED_ALPHANUMERICS);
659 set_bit (U_BOX_DRAWING);
660 set_bit (U_BLOCK_ELEMENTS);
661 set_bit (U_GEOMETRIC_SHAPES);
662 set_bit (U_MISCELLANEOUS_SYMBOLS);
663 set_bit (U_CJK_SYMBOLS_AND_PUNCTUATION);
664 set_bit (U_HIRAGANA);
665 set_bit (U_KATAKANA);
666 set_bit (U_BOPOMOFO);
667 set_bit (U_HANGUL_COMPATIBILITY_JAMO);
668 set_bit (U_CJK_MISCELLANEOUS);
669 set_bit (U_CJK_COMPATIBILITY);
671 set_bit (U_HANGUL_SUPPLEMENTARY_A);
672 set_bit (U_CJK_UNIFIED_IDEOGRAPHS);
673 set_bit (U_CJK_COMPATIBILITY_IDEOGRAPHS);
674 set_bit (U_ALPHABETIC_PRESENTATION_FORMS);
675 set_bit (U_SMALL_FORM_VARIANTS);
676 set_bit (U_ARABIC_PRESENTATION_FORMS_B);
677 set_bit (U_SPECIALS);
681 set_bit (U_BASIC_LATIN);
682 set_bit (U_LATIN_1_SUPPLEMENT);
683 set_bit (U_LATIN_EXTENDED_B);
684 set_bit (U_SPACING_MODIFIER_LETTERS);
685 set_bit (U_BASIC_HEBREW);
686 set_bit (U_HEBREW_EXTENDED);
687 set_bit (U_GENERAL_PUNCTUATION);
688 set_bit (U_LETTERLIKE_SYMBOLS);
692 set_bit (U_BASIC_LATIN);
693 set_bit (U_LATIN_1_SUPPLEMENT);
694 set_bit (U_LATIN_EXTENDED_A);
695 set_bit (U_LATIN_EXTENDED_B);
696 set_bit (U_SPACING_MODIFIER_LETTERS);
697 set_bit (U_BASIC_GREEK);
698 set_bit (U_BASIC_ARABIC);
699 set_bit (U_ARABIC_EXTENDED);
700 set_bit (U_GENERAL_PUNCTUATION);
701 set_bit (U_LETTERLIKE_SYMBOLS);
703 set_bit (U_MATHEMATICAL_OPERATORS);
704 set_bit (U_MISCELLANEOUS_TECHNICAL);
705 set_bit (U_BOX_DRAWING);
706 set_bit (U_BLOCK_ELEMENTS);
707 set_bit (U_GEOMETRIC_SHAPES);
708 set_bit (U_MISCELLANEOUS_SYMBOLS);
709 set_bit (U_HALFWIDTH_AND_FULLWIDTH_FORMS);
713 set_bit (U_BASIC_LATIN);
714 set_bit (U_LATIN_1_SUPPLEMENT);
715 set_bit (U_LATIN_EXTENDED_B);
716 set_bit (U_BASIC_GREEK);
717 set_bit (U_GENERAL_PUNCTUATION);
718 set_bit (U_SUPERSCRIPTS_AND_SUBSCRIPTS);
719 set_bit (U_LETTERLIKE_SYMBOLS);
721 set_bit (U_MATHEMATICAL_OPERATORS);
722 set_bit (U_MISCELLANEOUS_TECHNICAL);
723 set_bit (U_BOX_DRAWING);
724 set_bit (U_BLOCK_ELEMENTS);
725 set_bit (U_GEOMETRIC_SHAPES);
726 set_bit (U_MISCELLANEOUS_SYMBOLS);
729 case TURKISH_CHARSET:
730 set_bit (U_BASIC_LATIN);
731 set_bit (U_LATIN_1_SUPPLEMENT);
732 set_bit (U_LATIN_EXTENDED_A);
733 set_bit (U_LATIN_EXTENDED_B);
734 set_bit (U_SPACING_MODIFIER_LETTERS);
735 set_bit (U_BASIC_GREEK);
736 set_bit (U_GENERAL_PUNCTUATION);
737 set_bit (U_SUPERSCRIPTS_AND_SUBSCRIPTS);
738 set_bit (U_CURRENCY_SYMBOLS);
739 set_bit (U_LETTERLIKE_SYMBOLS);
741 set_bit (U_MATHEMATICAL_OPERATORS);
742 set_bit (U_MISCELLANEOUS_TECHNICAL);
743 set_bit (U_BOX_DRAWING);
744 set_bit (U_BLOCK_ELEMENTS);
745 set_bit (U_GEOMETRIC_SHAPES);
746 set_bit (U_MISCELLANEOUS_SYMBOLS);
749 case VIETNAMESE_CHARSET:
751 /* These are not in the table, so I have no idea */
754 set_bit (U_BASIC_LATIN);
755 set_bit (U_LATIN_1_SUPPLEMENT);
756 set_bit (U_LATIN_EXTENDED_A);
757 set_bit (U_LATIN_EXTENDED_B);
758 set_bit (U_SPACING_MODIFIER_LETTERS);
759 set_bit (U_BASIC_GREEK);
760 set_bit (U_GENERAL_PUNCTUATION);
761 set_bit (U_SUPERSCRIPTS_AND_SUBSCRIPTS);
762 set_bit (U_CURRENCY_SYMBOLS);
763 set_bit (U_LETTERLIKE_SYMBOLS);
765 set_bit (U_MATHEMATICAL_OPERATORS);
766 set_bit (U_MISCELLANEOUS_TECHNICAL);
767 set_bit (U_BOX_DRAWING);
768 set_bit (U_BLOCK_ELEMENTS);
769 set_bit (U_GEOMETRIC_SHAPES);
770 set_bit (U_MISCELLANEOUS_SYMBOLS);
773 case EASTEUROPE_CHARSET:
774 set_bit (U_BASIC_LATIN);
775 set_bit (U_LATIN_1_SUPPLEMENT);
776 set_bit (U_LATIN_EXTENDED_A);
777 set_bit (U_LATIN_EXTENDED_B);
778 set_bit (U_SPACING_MODIFIER_LETTERS);
779 set_bit (U_BASIC_GREEK);
780 set_bit (U_GENERAL_PUNCTUATION);
781 set_bit (U_SUPERSCRIPTS_AND_SUBSCRIPTS);
782 set_bit (U_CURRENCY_SYMBOLS);
783 set_bit (U_LETTERLIKE_SYMBOLS);
785 set_bit (U_MATHEMATICAL_OPERATORS);
786 set_bit (U_MISCELLANEOUS_TECHNICAL);
787 set_bit (U_BOX_DRAWING);
788 set_bit (U_BLOCK_ELEMENTS);
789 set_bit (U_GEOMETRIC_SHAPES);
790 set_bit (U_MISCELLANEOUS_SYMBOLS);
793 case RUSSIAN_CHARSET:
794 set_bit (U_BASIC_LATIN);
795 set_bit (U_LATIN_1_SUPPLEMENT);
796 set_bit (U_CYRILLIC);
797 set_bit (U_GENERAL_PUNCTUATION);
798 set_bit (U_LETTERLIKE_SYMBOLS);
800 set_bit (U_MATHEMATICAL_OPERATORS);
801 set_bit (U_MISCELLANEOUS_TECHNICAL);
802 set_bit (U_BOX_DRAWING);
803 set_bit (U_BLOCK_ELEMENTS);
804 set_bit (U_GEOMETRIC_SHAPES);
805 set_bit (U_MISCELLANEOUS_SYMBOLS);
814 static GdkWin32SingleFont *
815 gdk_font_load_logfont (LOGFONT *lfp)
817 GdkWin32SingleFont *singlefont;
825 for (tries = 0; ; tries++)
827 GDK_NOTE (MISC, g_print ("... trying %ld,%ld,%ld,%ld,"
830 "%d,%#.02x,\"%s\"\n",
831 lfp->lfHeight, lfp->lfWidth,
832 lfp->lfEscapement, lfp->lfOrientation,
833 lfp->lfWeight, lfp->lfItalic,
834 lfp->lfUnderline, lfp->lfStrikeOut,
836 lfp->lfOutPrecision, lfp->lfClipPrecision,
837 lfp->lfQuality, lfp->lfPitchAndFamily,
839 hfont = CreateFontIndirect (lfp);
844 /* If we fail, try some similar fonts often found on Windows. */
847 if (g_ascii_strcasecmp (lfp->lfFaceName, "helvetica") == 0)
848 strcpy (lfp->lfFaceName, "arial");
849 else if (g_ascii_strcasecmp (lfp->lfFaceName, "new century schoolbook") == 0)
850 strcpy (lfp->lfFaceName, "century schoolbook");
851 else if (g_ascii_strcasecmp (lfp->lfFaceName, "courier") == 0)
852 strcpy (lfp->lfFaceName, "courier new");
853 else if (g_ascii_strcasecmp (lfp->lfFaceName, "lucida") == 0)
854 strcpy (lfp->lfFaceName, "lucida sans unicode");
855 else if (g_ascii_strcasecmp (lfp->lfFaceName, "lucidatypewriter") == 0)
856 strcpy (lfp->lfFaceName, "lucida console");
857 else if (g_ascii_strcasecmp (lfp->lfFaceName, "times") == 0)
858 strcpy (lfp->lfFaceName, "times new roman");
862 if (g_ascii_strcasecmp (lfp->lfFaceName, "courier") == 0)
864 strcpy (lfp->lfFaceName, "");
865 lfp->lfPitchAndFamily |= FF_MODERN;
867 else if (g_ascii_strcasecmp (lfp->lfFaceName, "times new roman") == 0)
869 strcpy (lfp->lfFaceName, "");
870 lfp->lfPitchAndFamily |= FF_ROMAN;
872 else if (g_ascii_strcasecmp (lfp->lfFaceName, "helvetica") == 0
873 || g_ascii_strcasecmp (lfp->lfFaceName, "lucida") == 0)
875 strcpy (lfp->lfFaceName, "");
876 lfp->lfPitchAndFamily |= FF_SWISS;
880 strcpy (lfp->lfFaceName, "");
881 lfp->lfPitchAndFamily = (lfp->lfPitchAndFamily & 0x0F) | FF_DONTCARE;
892 singlefont = g_new (GdkWin32SingleFont, 1);
893 singlefont->hfont = hfont;
894 GetObject (singlefont->hfont, sizeof (logfont), &logfont);
895 oldfont = SelectObject (_gdk_display_hdc, singlefont->hfont);
896 memset (&singlefont->fs, 0, sizeof (singlefont->fs));
897 singlefont->charset = GetTextCharsetInfo (_gdk_display_hdc, &singlefont->fs, 0);
898 GetTextFace (_gdk_display_hdc, sizeof (face), face);
899 SelectObject (_gdk_display_hdc, oldfont);
900 if (TranslateCharsetInfo ((DWORD *) (gintptr) singlefont->charset, &csi,
902 && singlefont->charset != MAC_CHARSET)
903 singlefont->codepage = csi.ciACP;
905 singlefont->codepage = 0;
907 GDK_NOTE (MISC, (g_print ("... = %p %s cs %s cp%d\n",
908 singlefont->hfont, face,
909 charset_name (singlefont->charset),
910 singlefont->codepage),
911 g_print ("... Unicode subranges:"),
912 print_unicode_subranges (&singlefont->fs)));
913 if (check_unicode_subranges (singlefont->charset, &singlefont->fs))
914 GDK_NOTE (MISC, (g_print ("... Guesstimated Unicode subranges:"),
915 print_unicode_subranges (&singlefont->fs)));
920 static GdkWin32SingleFont *
921 gdk_font_load_internal (const gchar *font_name)
926 int numfields, n1, n2;
927 char foundry[32], family[100], weight[32], slant[32], set_width[32],
928 spacing[32], registry[32], encoding[32];
929 char pixel_size[10], point_size[10], res_x[10], res_y[10], avg_width[10];
934 g_return_val_if_fail (font_name != NULL, NULL);
936 GDK_NOTE (MISC, g_print ("gdk_font_load_internal: %s\n", font_name));
938 numfields = sscanf (font_name,
939 "-%30[^-]-%100[^-]-%30[^-]-%30[^-]-%30[^-]-%n",
948 /* Probably a plain Windows font name */
949 logfont.lfHeight = 0;
951 logfont.lfEscapement = 0;
952 logfont.lfOrientation = 0;
953 logfont.lfWeight = FW_DONTCARE;
954 logfont.lfItalic = FALSE;
955 logfont.lfUnderline = FALSE;
956 logfont.lfStrikeOut = FALSE;
957 logfont.lfCharSet = ANSI_CHARSET;
958 logfont.lfOutPrecision = OUT_TT_ONLY_PRECIS;
959 logfont.lfClipPrecision = CLIP_DEFAULT_PRECIS;
960 logfont.lfQuality = PROOF_QUALITY;
961 logfont.lfPitchAndFamily = DEFAULT_PITCH;
962 fn = g_filename_from_utf8 (font_name, -1, NULL, NULL, NULL);
963 strcpy (logfont.lfFaceName, fn);
966 else if (numfields != 5)
968 g_warning ("gdk_font_load: font name %s illegal", font_name);
973 /* It must be a XLFD name */
975 /* Check for hex escapes in the font family,
976 * put in there by logfont_to_xlfd. Convert them in-place.
981 if (*p == '%' && isxdigit (p[1]) && isxdigit (p[2]))
983 sscanf (p+1, "%2x", &c);
990 /* Skip add_style which often is empty in the requested font name */
991 while (font_name[n1] && font_name[n1] != '-')
995 numfields += sscanf (font_name + n1,
996 "-%8[^-]-%8[^-]-%8[^-]-%8[^-]-%30[^-]-%8[^-]-%30[^-]-%30[^-]%n",
1007 if (numfields != 14 || font_name[n1 + n2] != '\0')
1009 g_warning ("gdk_font_load: font name %s illegal", font_name);
1013 logpixelsy = GetDeviceCaps (_gdk_display_hdc, LOGPIXELSY);
1015 if (strcmp (pixel_size, "*") == 0)
1016 if (strcmp (point_size, "*") == 0)
1017 logfont.lfHeight = 0;
1019 logfont.lfHeight = -(int) (((double) atoi (point_size))/720.*logpixelsy);
1021 logfont.lfHeight = -atoi (pixel_size);
1023 logfont.lfWidth = 0;
1024 logfont.lfEscapement = 0;
1025 logfont.lfOrientation = 0;
1027 if (g_ascii_strcasecmp (weight, "thin") == 0)
1028 logfont.lfWeight = FW_THIN;
1029 else if (g_ascii_strcasecmp (weight, "extralight") == 0)
1030 logfont.lfWeight = FW_EXTRALIGHT;
1031 else if (g_ascii_strcasecmp (weight, "ultralight") == 0)
1032 #ifdef FW_ULTRALIGHT
1033 logfont.lfWeight = FW_ULTRALIGHT;
1035 logfont.lfWeight = FW_EXTRALIGHT; /* In fact, FW_ULTRALIGHT really is
1036 * defined as FW_EXTRALIGHT anyway.
1039 else if (g_ascii_strcasecmp (weight, "light") == 0)
1040 logfont.lfWeight = FW_LIGHT;
1041 else if (g_ascii_strcasecmp (weight, "normal") == 0)
1042 logfont.lfWeight = FW_NORMAL;
1043 else if (g_ascii_strcasecmp (weight, "regular") == 0)
1044 logfont.lfWeight = FW_REGULAR;
1045 else if (g_ascii_strcasecmp (weight, "medium") == 0)
1046 logfont.lfWeight = FW_MEDIUM;
1047 else if (g_ascii_strcasecmp (weight, "semibold") == 0)
1048 logfont.lfWeight = FW_SEMIBOLD;
1049 else if (g_ascii_strcasecmp (weight, "demibold") == 0)
1051 logfont.lfWeight = FW_DEMIBOLD;
1053 logfont.lfWeight = FW_SEMIBOLD; /* As above */
1055 else if (g_ascii_strcasecmp (weight, "bold") == 0)
1056 logfont.lfWeight = FW_BOLD;
1057 else if (g_ascii_strcasecmp (weight, "extrabold") == 0)
1058 logfont.lfWeight = FW_EXTRABOLD;
1059 else if (g_ascii_strcasecmp (weight, "ultrabold") == 0)
1061 logfont.lfWeight = FW_ULTRABOLD;
1063 logfont.lfWeight = FW_EXTRABOLD; /* As above */
1065 else if (g_ascii_strcasecmp (weight, "heavy") == 0)
1066 logfont.lfWeight = FW_HEAVY;
1067 else if (g_ascii_strcasecmp (weight, "black") == 0)
1069 logfont.lfWeight = FW_BLACK;
1071 logfont.lfWeight = FW_HEAVY; /* As above */
1074 logfont.lfWeight = FW_DONTCARE;
1076 if (g_ascii_strcasecmp (slant, "italic") == 0
1077 || g_ascii_strcasecmp (slant, "oblique") == 0
1078 || g_ascii_strcasecmp (slant, "i") == 0
1079 || g_ascii_strcasecmp (slant, "o") == 0)
1080 logfont.lfItalic = TRUE;
1082 logfont.lfItalic = FALSE;
1083 logfont.lfUnderline = FALSE;
1084 logfont.lfStrikeOut = FALSE;
1085 if (g_ascii_strcasecmp (registry, "iso8859") == 0)
1086 if (strcmp (encoding, "1") == 0)
1087 logfont.lfCharSet = ANSI_CHARSET;
1088 else if (strcmp (encoding, "2") == 0)
1089 logfont.lfCharSet = EASTEUROPE_CHARSET;
1090 else if (strcmp (encoding, "7") == 0)
1091 logfont.lfCharSet = GREEK_CHARSET;
1092 else if (strcmp (encoding, "8") == 0)
1093 logfont.lfCharSet = HEBREW_CHARSET;
1094 else if (strcmp (encoding, "9") == 0)
1095 logfont.lfCharSet = TURKISH_CHARSET;
1097 logfont.lfCharSet = ANSI_CHARSET; /* XXX ??? */
1098 else if (g_ascii_strcasecmp (registry, "jisx0208.1983") == 0)
1099 logfont.lfCharSet = SHIFTJIS_CHARSET;
1100 else if (g_ascii_strcasecmp (registry, "ksc5601.1987") == 0)
1101 logfont.lfCharSet = HANGEUL_CHARSET;
1102 else if (g_ascii_strcasecmp (registry, "gb2312.1980") == 0)
1103 logfont.lfCharSet = GB2312_CHARSET;
1104 else if (g_ascii_strcasecmp (registry, "big5") == 0)
1105 logfont.lfCharSet = CHINESEBIG5_CHARSET;
1106 else if (g_ascii_strcasecmp (registry, "windows") == 0
1107 || g_ascii_strcasecmp (registry, "microsoft") == 0)
1108 if (g_ascii_strcasecmp (encoding, "symbol") == 0)
1109 logfont.lfCharSet = SYMBOL_CHARSET;
1110 else if (g_ascii_strcasecmp (encoding, "shiftjis") == 0)
1111 logfont.lfCharSet = SHIFTJIS_CHARSET;
1112 else if (g_ascii_strcasecmp (encoding, "gb2312") == 0)
1113 logfont.lfCharSet = GB2312_CHARSET;
1114 else if (g_ascii_strcasecmp (encoding, "hangeul") == 0)
1115 logfont.lfCharSet = HANGEUL_CHARSET;
1116 else if (g_ascii_strcasecmp (encoding, "big5") == 0)
1117 logfont.lfCharSet = CHINESEBIG5_CHARSET;
1118 else if (g_ascii_strcasecmp (encoding, "johab") == 0)
1119 logfont.lfCharSet = JOHAB_CHARSET;
1120 else if (g_ascii_strcasecmp (encoding, "hebrew") == 0)
1121 logfont.lfCharSet = HEBREW_CHARSET;
1122 else if (g_ascii_strcasecmp (encoding, "arabic") == 0)
1123 logfont.lfCharSet = ARABIC_CHARSET;
1124 else if (g_ascii_strcasecmp (encoding, "greek") == 0)
1125 logfont.lfCharSet = GREEK_CHARSET;
1126 else if (g_ascii_strcasecmp (encoding, "turkish") == 0)
1127 logfont.lfCharSet = TURKISH_CHARSET;
1128 else if (g_ascii_strcasecmp (encoding, "easteurope") == 0)
1129 logfont.lfCharSet = EASTEUROPE_CHARSET;
1130 else if (g_ascii_strcasecmp (encoding, "russian") == 0)
1131 logfont.lfCharSet = RUSSIAN_CHARSET;
1132 else if (g_ascii_strcasecmp (encoding, "mac") == 0)
1133 logfont.lfCharSet = MAC_CHARSET;
1134 else if (g_ascii_strcasecmp (encoding, "baltic") == 0)
1135 logfont.lfCharSet = BALTIC_CHARSET;
1136 else if (g_ascii_strcasecmp (encoding, "cp1251") == 0)
1137 logfont.lfCharSet = RUSSIAN_CHARSET;
1139 logfont.lfCharSet = ANSI_CHARSET; /* XXX ??? */
1141 logfont.lfCharSet = ANSI_CHARSET; /* XXX ??? */
1142 logfont.lfOutPrecision = OUT_TT_PRECIS;
1143 logfont.lfClipPrecision = CLIP_DEFAULT_PRECIS;
1144 logfont.lfQuality = PROOF_QUALITY;
1145 if (g_ascii_strcasecmp (spacing, "m") == 0)
1146 logfont.lfPitchAndFamily = FIXED_PITCH;
1147 else if (g_ascii_strcasecmp (spacing, "p") == 0)
1148 logfont.lfPitchAndFamily = VARIABLE_PITCH;
1150 logfont.lfPitchAndFamily = DEFAULT_PITCH;
1151 fn = g_filename_from_utf8 (family, -1, NULL, NULL, NULL);
1152 strcpy (logfont.lfFaceName, fn);
1156 return gdk_font_load_logfont (&logfont);
1160 gdk_font_from_one_singlefont (GdkWin32SingleFont *singlefont)
1163 GdkFontPrivateWin32 *private;
1165 TEXTMETRIC textmetric;
1167 private = g_new (GdkFontPrivateWin32, 1);
1168 font = (GdkFont*) private;
1170 private->base.ref_count = 1;
1171 private->names = NULL;
1172 private->fonts = g_slist_append (NULL, singlefont);
1174 /* Pretend all fonts are fontsets... Gtktext and gtkentry work better
1175 * that way, they use wide chars, which is necessary for non-ASCII
1176 * chars to work. (Yes, even Latin-1, as we use Unicode internally.)
1178 font->type = GDK_FONT_FONTSET;
1179 oldfont = SelectObject (_gdk_display_hdc, singlefont->hfont);
1180 GetTextMetrics (_gdk_display_hdc, &textmetric);
1181 SelectObject (_gdk_display_hdc, oldfont);
1182 font->ascent = textmetric.tmAscent;
1183 font->descent = textmetric.tmDescent;
1185 GDK_NOTE (MISC, g_print ("... asc %d desc %d\n",
1186 font->ascent, font->descent));
1192 gdk_fontset_load (const gchar *fontset_name)
1195 GdkFontPrivateWin32 *private;
1196 GdkWin32SingleFont *singlefont;
1198 TEXTMETRIC textmetric;
1202 g_return_val_if_fail (fontset_name != NULL, NULL);
1204 font = gdk_font_hash_lookup (GDK_FONT_FONTSET, fontset_name);
1208 s = fs = g_strdup (fontset_name);
1209 while (*s && isspace (*s))
1212 g_return_val_if_fail (*s, NULL);
1214 private = g_new (GdkFontPrivateWin32, 1);
1215 font = (GdkFont*) private;
1217 private->base.ref_count = 1;
1218 private->names = NULL;
1219 private->fonts = NULL;
1221 font->type = GDK_FONT_FONTSET;
1227 if ((p = strchr (s, ',')) != NULL)
1232 while (isspace (b[-1]))
1235 singlefont = gdk_font_load_internal (s);
1238 private->fonts = g_slist_append (private->fonts, singlefont);
1239 oldfont = SelectObject (_gdk_display_hdc, singlefont->hfont);
1240 GetTextMetrics (_gdk_display_hdc, &textmetric);
1241 SelectObject (_gdk_display_hdc, oldfont);
1242 font->ascent = MAX (font->ascent, textmetric.tmAscent);
1243 font->descent = MAX (font->descent, textmetric.tmDescent);
1248 while (*s && isspace (*s))
1259 gdk_font_hash_insert (GDK_FONT_FONTSET, font, fontset_name);
1265 gdk_fontset_load_for_display (GdkDisplay *display,
1266 const gchar *fontset_name)
1268 g_return_val_if_fail (GDK_IS_DISPLAY (display), NULL);
1270 return gdk_fontset_load (fontset_name);
1274 _gdk_font_destroy (GdkFont *font)
1276 GdkFontPrivateWin32 *private = (GdkFontPrivateWin32 *) font;
1277 GdkWin32SingleFont *singlefont;
1280 singlefont = (GdkWin32SingleFont *) private->fonts->data;
1281 GDK_NOTE (MISC, g_print ("_gdk_font_destroy %p\n",
1282 singlefont->hfont));
1284 gdk_font_hash_remove (font->type, font);
1289 DeleteObject (singlefont->hfont);
1292 case GDK_FONT_FONTSET:
1293 list = private->fonts;
1296 singlefont = (GdkWin32SingleFont *) list->data;
1297 DeleteObject (singlefont->hfont);
1301 g_slist_free (private->fonts);
1308 _gdk_font_strlen (GdkFont *font,
1311 g_return_val_if_fail (font != NULL, -1);
1312 g_return_val_if_fail (str != NULL, -1);
1314 return strlen (str);
1318 gdk_font_id (const GdkFont *font)
1320 const GdkFontPrivateWin32 *private;
1322 g_return_val_if_fail (font != NULL, 0);
1324 private = (const GdkFontPrivateWin32 *) font;
1326 /* FIXME: What to do on Win64? */
1327 if (font->type == GDK_FONT_FONT)
1328 return (gint) (gintptr) ((GdkWin32SingleFont *) private->fonts->data)->hfont;
1334 gdk_font_equal (const GdkFont *fonta,
1335 const GdkFont *fontb)
1337 const GdkFontPrivateWin32 *privatea;
1338 const GdkFontPrivateWin32 *privateb;
1340 g_return_val_if_fail (fonta != NULL, FALSE);
1341 g_return_val_if_fail (fontb != NULL, FALSE);
1343 privatea = (const GdkFontPrivateWin32 *) fonta;
1344 privateb = (const GdkFontPrivateWin32 *) fontb;
1346 if (fonta->type == GDK_FONT_FONT && fontb->type == GDK_FONT_FONT)
1347 return (((GdkWin32SingleFont *) privatea->fonts->data)->hfont
1348 == ((GdkWin32SingleFont *) privateb->fonts->data)->hfont);
1349 else if (fonta->type == GDK_FONT_FONTSET && fontb->type == GDK_FONT_FONTSET)
1351 GSList *lista = privatea->fonts;
1352 GSList *listb = privateb->fonts;
1354 while (lista && listb)
1356 if (((GdkWin32SingleFont *) lista->data)->hfont
1357 != ((GdkWin32SingleFont *) listb->data)->hfont)
1359 lista = lista->next;
1360 listb = listb->next;
1371 /* Return the Unicode Subset bitfield number for a Unicode character */
1374 unicode_classify (wchar_t wc)
1377 int max = G_N_ELEMENTS (utab) - 1;
1382 mid = (min + max) / 2;
1383 if (utab[mid].high < wc)
1385 else if (wc < utab[mid].low)
1387 else if (utab[mid].low <= wc && wc <= utab[mid].high)
1388 return utab[mid].bit;
1392 /* Fallback... returning -1 might cause problems. Returning
1393 * U_BASIC_LATIN won't help handling strange characters, but won't
1396 return U_BASIC_LATIN;
1400 _gdk_wchar_text_handle (GdkFont *font,
1401 const wchar_t *wcstr,
1403 void (*handler)(GdkWin32SingleFont *,
1409 GdkFontPrivateWin32 *private;
1410 GdkWin32SingleFont *singlefont;
1413 const wchar_t *start, *end, *wcp;
1417 private = (GdkFontPrivateWin32 *) font;
1419 g_assert (private->base.ref_count > 0);
1421 GDK_NOTE (MISC, g_print ("_gdk_wchar_text_handle: "));
1425 /* Split Unicode string into pieces of the same class */
1427 block = unicode_classify (*wcp);
1428 while (wcp + 1 < end && unicode_classify (wcp[1]) == block)
1431 /* Find a font in the fontset that can handle this class */
1432 list = private->fonts;
1435 singlefont = (GdkWin32SingleFont *) list->data;
1437 if (singlefont->fs.fsUsb[block/32] & (1 << (block % 32)))
1446 GDK_NOTE (MISC, g_print ("%" G_GSIZE_FORMAT ":%" G_GSIZE_FORMAT ":%d:%p ",
1447 start-wcstr, wcp-wcstr, block,
1448 (singlefont ? singlefont->hfont : 0)));
1450 /* Call the callback function */
1451 (*handler) (singlefont, start, wcp+1 - start, arg);
1454 GDK_NOTE (MISC, g_print ("\n"));
1458 gdk_font_get_display (GdkFont* font)
1460 return _gdk_display;