yaze 0.2.0
Link to the Past ROM Editor
 
Loading...
Searching...
No Matches
font_loader.cc
Go to the documentation of this file.
2
3#include <string>
4#include <unordered_set>
5#include <vector>
6#include <filesystem>
7
8#include "absl/status/status.h"
9#include "absl/strings/str_cat.h"
10#include "absl/strings/str_format.h"
12#include "app/gui/icons.h"
13#include "imgui/imgui.h"
14
15namespace yaze {
16namespace app {
17namespace core {
18
19absl::Status LoadPackageFonts() {
20 ImGuiIO &io = ImGui::GetIO();
21
22 static const char *KARLA_REGULAR = "Karla-Regular.ttf";
23 static const char *ROBOTO_MEDIUM = "Roboto-Medium.ttf";
24 static const char *COUSINE_REGULAR = "Cousine-Regular.ttf";
25 static const char *DROID_SANS = "DroidSans.ttf";
26 static const char *NOTO_SANS_JP = "NotoSansJP.ttf";
27 static const char *IBM_PLEX_JP = "IBMPlexSansJP-Bold.ttf";
28 static const float FONT_SIZE_DEFAULT = 16.0f;
29 static const float FONT_SIZE_DROID_SANS = 18.0f;
30 static const float ICON_FONT_SIZE = 18.0f;
31
32 // Icon configuration
33 static const ImWchar icons_ranges[] = {ICON_MIN_MD, 0xf900, 0};
34 ImFontConfig icons_config;
35 icons_config.MergeMode = true;
36 icons_config.GlyphOffset.y = 5.0f;
37 icons_config.GlyphMinAdvanceX = 13.0f;
38 icons_config.PixelSnapH = true;
39
40 // Japanese font configuration
41 ImFontConfig japanese_font_config;
42 japanese_font_config.MergeMode = true;
43 icons_config.GlyphOffset.y = 5.0f;
44 icons_config.GlyphMinAdvanceX = 13.0f;
45 icons_config.PixelSnapH = true;
46
47 // List of fonts to be loaded
48 std::vector<const char *> font_paths = {
49 KARLA_REGULAR, ROBOTO_MEDIUM, COUSINE_REGULAR, IBM_PLEX_JP, DROID_SANS};
50
51 // Load fonts with associated icon and Japanese merges
52 for (const auto &font_path : font_paths) {
53 float font_size =
54 (font_path == DROID_SANS) ? FONT_SIZE_DROID_SANS : FONT_SIZE_DEFAULT;
55
56 std::string actual_font_path;
57#ifdef __APPLE__
58#if TARGET_OS_IOS == 1
59 const std::string kBundlePath = GetBundleResourcePath();
60 actual_font_path = kBundlePath + font_path;
61#else
62 actual_font_path = absl::StrCat(GetBundleResourcePath(),
63 "Contents/Resources/font/", font_path);
64#endif
65#else
66 actual_font_path = std::filesystem::absolute(font_path).string();
67#endif
68
69 if (!io.Fonts->AddFontFromFileTTF(actual_font_path.data(), font_size)) {
70 return absl::InternalError(
71 absl::StrFormat("Failed to load font from %s", actual_font_path));
72 }
73
74 // Merge icon set
75 std::string actual_icon_font_path = "";
76 const char *icon_font_path = FONT_ICON_FILE_NAME_MD;
77#if defined(__APPLE__) && defined(__MACH__)
78#if TARGET_OS_IOS == 1
79 const std::string kIconBundlePath = GetBundleResourcePath();
80 actual_icon_font_path = kIconBundlePath + "MaterialIcons-Regular.ttf";
81#else
82 actual_icon_font_path =
83 absl::StrCat(GetBundleResourcePath(),
84 "Contents/Resources/font/MaterialIcons-Regular.ttf");
85#endif
86#else
87 actual_icon_font_path = std::filesystem::absolute(icon_font_path).string();
88#endif
89 io.Fonts->AddFontFromFileTTF(actual_icon_font_path.data(), ICON_FONT_SIZE,
90 &icons_config, icons_ranges);
91
92 // Merge Japanese font
93 std::string actual_japanese_font_path = "";
94 const char *japanese_font_path = NOTO_SANS_JP;
95#if defined(__APPLE__) && defined(__MACH__)
96#if TARGET_OS_IOS == 1
97 const std::string kJapaneseBundlePath = GetBundleResourcePath();
98 actual_japanese_font_path = kJapaneseBundlePath + japanese_font_path;
99#else
100 actual_japanese_font_path =
101 absl::StrCat(GetBundleResourcePath(), "Contents/Resources/font/",
102 japanese_font_path);
103#endif
104#else
105 actual_japanese_font_path =
106 std::filesystem::absolute(japanese_font_path).string();
107#endif
108 io.Fonts->AddFontFromFileTTF(actual_japanese_font_path.data(), 18.0f,
109 &japanese_font_config,
110 io.Fonts->GetGlyphRangesJapanese());
111 }
112 return absl::OkStatus();
113}
114
115#ifdef _WIN32
116#include <Windows.h>
117
118int CALLBACK EnumFontFamExProc(const LOGFONT *lpelfe, const TEXTMETRIC *lpntme,
119 DWORD FontType, LPARAM lParam) {
120 // Step 3: Load the font into ImGui
121 ImGuiIO &io = ImGui::GetIO();
122 io.Fonts->AddFontFromFileTTF(lpelfe->lfFaceName, 16.0f);
123
124 return 1;
125}
126
127void LoadSystemFonts() {
128 HKEY hKey;
129 std::vector<std::string> fontPaths;
130
131 // Open the registry key where fonts are listed
132 if (RegOpenKeyEx(
133 HKEY_LOCAL_MACHINE,
134 TEXT("SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Fonts"), 0,
135 KEY_READ, &hKey) == ERROR_SUCCESS) {
136 DWORD valueCount;
137 DWORD maxValueNameSize;
138 DWORD maxValueDataSize;
139
140 // Query the number of entries and the maximum size of the names and values
141 RegQueryInfoKey(hKey, NULL, NULL, NULL, NULL, NULL, NULL, &valueCount,
142 &maxValueNameSize, &maxValueDataSize, NULL, NULL);
143
144 char *valueName = new char[maxValueNameSize + 1]; // +1 for null terminator
145 BYTE *valueData = new BYTE[maxValueDataSize + 1]; // +1 for null terminator
146
147 // Enumerate all font entries
148 for (DWORD i = 0; i < valueCount; i++) {
149 DWORD valueNameSize = maxValueNameSize + 1; // +1 for null terminator
150 DWORD valueDataSize = maxValueDataSize + 1; // +1 for null terminator
151 DWORD valueType;
152
153 // Clear buffers
154 memset(valueName, 0, valueNameSize);
155 memset(valueData, 0, valueDataSize);
156
157 // Get the font name and file path
158 if (RegEnumValue(hKey, i, valueName, &valueNameSize, NULL, &valueType,
159 valueData, &valueDataSize) == ERROR_SUCCESS) {
160 if (valueType == REG_SZ) {
161 // Add the font file path to the vector
162 std::string fontPath(reinterpret_cast<char *>(valueData),
163 valueDataSize);
164
165 fontPaths.push_back(fontPath);
166 }
167 }
168 }
169
170 delete[] valueName;
171 delete[] valueData;
172
173 RegCloseKey(hKey);
174 }
175
176 ImGuiIO &io = ImGui::GetIO();
177
178 // List of common font face names
179 static const std::unordered_set<std::string> commonFontFaceNames = {
180 "arial",
181 "times",
182 "cour",
183 "verdana",
184 "tahoma",
185 "comic",
186 "Impact",
187 "ariblk",
188 "Trebuchet MS",
189 "Georgia",
190 "Palatino Linotype",
191 "Lucida Sans Unicode",
192 "Tahoma",
193 "Lucida Console"};
194
195 for (auto &fontPath : fontPaths) {
196 // Check if the font path has a "C:\" prefix
197 if (fontPath.substr(0, 2) != "C:") {
198 // Add "C:\Windows\Fonts\" prefix to the font path
199 fontPath = absl::StrFormat("C:\\Windows\\Fonts\\%s", fontPath.c_str());
200 }
201
202 // Check if the font file has a .ttf or .TTF extension
203 std::string extension = fontPath.substr(fontPath.find_last_of(".") + 1);
204 if (extension == "ttf" || extension == "TTF") {
205 // Get the font face name from the font path
206 std::string fontFaceName =
207 fontPath.substr(fontPath.find_last_of("\\/") + 1);
208 fontFaceName = fontFaceName.substr(0, fontFaceName.find_last_of("."));
209
210 // Check if the font face name is in the common font face names list
211 if (commonFontFaceNames.find(fontFaceName) != commonFontFaceNames.end()) {
212 io.Fonts->AddFontFromFileTTF(fontPath.c_str(), 16.0f);
213
214 // Merge icon set
215 // Icon configuration
216 static const ImWchar icons_ranges[] = {ICON_MIN_MD, 0xf900, 0};
217 ImFontConfig icons_config;
218 static const float ICON_FONT_SIZE = 18.0f;
219 icons_config.MergeMode = true;
220 icons_config.GlyphOffset.y = 5.0f;
221 icons_config.GlyphMinAdvanceX = 13.0f;
222 icons_config.PixelSnapH = true;
223 io.Fonts->AddFontFromFileTTF(FONT_ICON_FILE_NAME_MD, ICON_FONT_SIZE,
224 &icons_config, icons_ranges);
225 }
226 }
227 }
228}
229
230#elif defined(__linux__)
231
232void LoadSystemFonts() {
233 // Load Linux System Fonts into ImGui
234 // ...
235}
236
237#endif
238
239} // namespace core
240} // namespace app
241} // namespace yaze
#define ICON_MIN_MD
Definition icons.h:8
#define FONT_ICON_FILE_NAME_MD
Definition icons.h:6
void LoadSystemFonts()
absl::Status LoadPackageFonts()
std::string GetBundleResourcePath()
GetBundleResourcePath returns the path to the bundle resource directory. Specific to MacOS.
Definition common.cc:22