Mercurial > repos > blastem
comparison nuklear_ui/font_win.c @ 1541:f8ef74e7c800
Merged nuklear_ui into default
author | Michael Pavone <pavone@retrodev.com> |
---|---|
date | Sun, 25 Mar 2018 12:01:49 -0700 |
parents | 982c5327dfcc |
children | cb12667aa83e |
comparison
equal
deleted
inserted
replaced
1533:78b7fc03c7c6 | 1541:f8ef74e7c800 |
---|---|
1 #include <windows.h> | |
2 #include <shlobj.h> | |
3 #include <string.h> | |
4 #include "../paths.h" | |
5 #include "../util.h" | |
6 #include "sfnt.h" | |
7 | |
8 uint8_t *default_font(uint32_t *size_out) | |
9 { | |
10 static const char *thin[] = {"Thin", NULL}; | |
11 static const char *extra_light[] = {"ExtraLight", "UltraLight", NULL}; | |
12 static const char *light[] = {"Light", NULL}; | |
13 static const char *regular[] = {"Regular", "Normal", "Book", NULL}; | |
14 static const char *medium[] = {"Medium", NULL}; | |
15 static const char *semi_bold[] = {"SemiBold", "DemiBold", NULL}; | |
16 static const char *bold[] = {"Bold", NULL}; | |
17 static const char *extra_bold[] = {"ExtraBold", "UltraBold", NULL}; | |
18 static const char *heavy[] = {"Heavy", "Black", NULL}; | |
19 static const char **weight_to_subfamilies[] = { | |
20 NULL, | |
21 thin, | |
22 extra_light, | |
23 light, | |
24 regular, | |
25 medium, | |
26 semi_bold, | |
27 bold, | |
28 extra_bold, | |
29 heavy | |
30 }; | |
31 | |
32 NONCLIENTMETRICSA metrics = { | |
33 .cbSize = sizeof(metrics) | |
34 }; | |
35 char *pref_name = NULL, *pref_prefix = NULL; | |
36 const char **pref_sub_families; | |
37 if (SystemParametersInfoA(SPI_GETNONCLIENTMETRICS, sizeof(metrics), &metrics, 0)) { | |
38 pref_name = metrics.lfMenuFont.lfFaceName; | |
39 int32_t weight = metrics.lfMenuFont.lfWeight / 100; | |
40 if (weight < 1 || weight > 9) { | |
41 weight = 4; | |
42 } | |
43 printf("Preferred family: %s, weight: %d\n", pref_name, weight); | |
44 pref_sub_families = weight_to_subfamilies[weight]; | |
45 } | |
46 if (pref_name) { | |
47 uint32_t prefix_len = 0; | |
48 while (pref_name[prefix_len] && pref_name[prefix_len] != ' ') | |
49 { | |
50 prefix_len++; | |
51 } | |
52 pref_prefix = malloc(prefix_len + 1); | |
53 memcpy(pref_prefix, pref_name, prefix_len); | |
54 pref_prefix[prefix_len] = 0; | |
55 } | |
56 sfnt_table *selected = NULL; | |
57 char windows[MAX_PATH]; | |
58 SHGetFolderPathA(NULL, CSIDL_WINDOWS, NULL, 0, windows); | |
59 char *fonts = path_append(windows, "Fonts"); | |
60 size_t num_entries; | |
61 char *tahoma = NULL, *arial = NULL; | |
62 dir_entry *entries = get_dir_list(fonts, &num_entries); | |
63 char *path = NULL; | |
64 for (size_t i = 0; i < num_entries; i++) | |
65 { | |
66 if (entries[i].is_dir) { | |
67 continue; | |
68 } | |
69 char *ext = path_extension(entries[i].name); | |
70 if (!ext || (strcasecmp(ext, "ttf") && strcasecmp(ext, "ttc") && strcasecmp(ext, "dfont"))) { | |
71 //not a truetype font, ignore | |
72 free(ext); | |
73 continue; | |
74 } | |
75 free(ext); | |
76 char *base = basename_no_extension(entries[i].name); | |
77 printf("basename: %s\n", base); | |
78 if (pref_prefix && !strncasecmp(base, pref_prefix, 6)) { | |
79 path = path_append(fonts, entries[i].name); | |
80 FILE *f = fopen(path, "rb"); | |
81 if (f) | |
82 { | |
83 long font_size = file_size(f); | |
84 uint8_t *blob = malloc(font_size); | |
85 if (font_size == fread(blob, 1, font_size, f)) | |
86 { | |
87 sfnt_container *sfnt = load_sfnt(blob, font_size); | |
88 if (sfnt) { | |
89 selected = sfnt_subfamily_by_names(sfnt, pref_sub_families); | |
90 if (!selected) { | |
91 sfnt_free(sfnt); | |
92 } | |
93 } else { | |
94 free(blob); | |
95 } | |
96 } else { | |
97 free(blob); | |
98 } | |
99 fclose(f); | |
100 } | |
101 free(path); | |
102 free(base); | |
103 if (selected) { | |
104 printf("Found preferred font in %s\n", entries[i].name); | |
105 break; | |
106 } | |
107 } else if (!strcasecmp(base, "tahoma")) { | |
108 tahoma = entries[i].name; | |
109 } else if (!strcasecmp(base, "arial")) { | |
110 arial = entries[i].name; | |
111 } | |
112 free(base); | |
113 } | |
114 if (!selected) { | |
115 path = NULL; | |
116 if (tahoma) { | |
117 path = path_append(fonts, tahoma); | |
118 } else if (arial) { | |
119 path = path_append(fonts, arial); | |
120 } | |
121 if (path) { | |
122 FILE *f = fopen(path, "rb"); | |
123 if (f) | |
124 { | |
125 long font_size = file_size(f); | |
126 uint8_t *blob = malloc(font_size); | |
127 if (font_size == fread(blob, 1, font_size, f)) | |
128 { | |
129 sfnt_container *sfnt = load_sfnt(blob, font_size); | |
130 if (sfnt) { | |
131 selected = sfnt->tables; | |
132 } else { | |
133 free(blob); | |
134 } | |
135 } | |
136 fclose(f); | |
137 } | |
138 free(path); | |
139 } | |
140 } | |
141 free(fonts); | |
142 free_dir_list(entries, num_entries); | |
143 if (selected) { | |
144 return sfnt_flatten(selected, size_out); | |
145 } | |
146 return NULL; | |
147 } |