summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/fontpack.c89
-rw-r--r--src/ui/text.c5
-rw-r--r--src/ui/util.c39
3 files changed, 95 insertions, 38 deletions
diff --git a/src/fontpack.c b/src/fontpack.c
index 3b42e848..ca1d1582 100644
--- a/src/fontpack.c
+++ b/src/fontpack.c
@@ -21,17 +21,18 @@ ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
21SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ 21SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
22 22
23#include "fontpack.h" 23#include "fontpack.h"
24#include "embedded.h"
25#include "app.h"
24 26
25#include <the_Foundation/archive.h> 27#include <the_Foundation/archive.h>
26#include <the_Foundation/array.h> 28#include <the_Foundation/array.h>
27#include <the_Foundation/file.h> 29#include <the_Foundation/file.h>
30#include <the_Foundation/fileinfo.h>
28#include <the_Foundation/path.h> 31#include <the_Foundation/path.h>
29#include <the_Foundation/ptrarray.h> 32#include <the_Foundation/ptrarray.h>
30#include <the_Foundation/string.h> 33#include <the_Foundation/string.h>
31#include <the_Foundation/toml.h> 34#include <the_Foundation/toml.h>
32 35
33#include "embedded.h"
34
35/* TODO: Clean up and/or reorder this file, it's a bit unorganized. */ 36/* TODO: Clean up and/or reorder this file, it's a bit unorganized. */
36 37
37float scale_FontSize(enum iFontSize size) { 38float scale_FontSize(enum iFontSize size) {
@@ -196,10 +197,13 @@ void init_FontPack(iFontPack *d) {
196} 197}
197 198
198void deinit_FontPack(iFontPack *d) { 199void deinit_FontPack(iFontPack *d) {
200 delete_String(d->loadPath);
199 iForEach(Array, i, &d->fonts) { 201 iForEach(Array, i, &d->fonts) {
200 deinit_FontSpec(i.value); 202 deinit_FontSpec(i.value);
201 } 203 }
202 deinit_Array(&d->fonts); 204 deinit_Array(&d->fonts);
205 iAssert(d->archive == NULL);
206 iAssert(d->loadSpec == NULL);
203} 207}
204 208
205iDefineTypeConstruction(FontPack) 209iDefineTypeConstruction(FontPack)
@@ -208,8 +212,11 @@ void handleIniTable_FontPack_(void *context, const iString *table, iBool isStart
208 iFontPack *d = context; 212 iFontPack *d = context;
209 if (isStart) { 213 if (isStart) {
210 iAssert(!d->loadSpec); 214 iAssert(!d->loadSpec);
211 d->loadSpec = new_FontSpec(); 215 /* Each font ID must be unique. */
212 set_String(&d->loadSpec->id, table); 216 if (!findSpec_Fonts(cstr_String(table))) {
217 d->loadSpec = new_FontSpec();
218 set_String(&d->loadSpec->id, table);
219 }
213 } 220 }
214 else { 221 else {
215 /* Set fallback font files. */ { 222 /* Set fallback font files. */ {
@@ -265,7 +272,8 @@ void handleIniKeyValue_FontPack_(void *context, const iString *table, const iStr
265 d->loadSpec->priority = (int) value->value.int64; 272 d->loadSpec->priority = (int) value->value.int64;
266 } 273 }
267 else if (!cmp_String(key, "height")) { 274 else if (!cmp_String(key, "height")) {
268 d->loadSpec->heightScale[0] = d->loadSpec->heightScale[1] = (float) number_TomlValue(value); 275 d->loadSpec->heightScale[0] = d->loadSpec->heightScale[1] =
276 iMin(2.0f, (float) number_TomlValue(value));
269 } 277 }
270 else if (!cmp_String(key, "glyphscale")) { 278 else if (!cmp_String(key, "glyphscale")) {
271 d->loadSpec->glyphScale[0] = d->loadSpec->glyphScale[1] = (float) number_TomlValue(value); 279 d->loadSpec->glyphScale[0] = d->loadSpec->glyphScale[1] = (float) number_TomlValue(value);
@@ -277,7 +285,7 @@ void handleIniKeyValue_FontPack_(void *context, const iString *table, const iStr
277 else if (startsWith_String(key, "ui.") || startsWith_String(key, "doc.")) { 285 else if (startsWith_String(key, "ui.") || startsWith_String(key, "doc.")) {
278 const int scope = startsWith_String(key, "ui.") ? 0 : 1; 286 const int scope = startsWith_String(key, "ui.") ? 0 : 1;
279 if (endsWith_String(key, ".height")) { 287 if (endsWith_String(key, ".height")) {
280 d->loadSpec->heightScale[scope] = (float) number_TomlValue(value); 288 d->loadSpec->heightScale[scope] = iMin(2.0f, (float) number_TomlValue(value));
281 } 289 }
282 if (endsWith_String(key, ".glyphscale")) { 290 if (endsWith_String(key, ".glyphscale")) {
283 d->loadSpec->glyphScale[scope] = (float) number_TomlValue(value); 291 d->loadSpec->glyphScale[scope] = (float) number_TomlValue(value);
@@ -330,18 +338,12 @@ void handleIniKeyValue_FontPack_(void *context, const iString *table, const iStr
330static iBool load_FontPack_(iFontPack *d, const iString *ini) { 338static iBool load_FontPack_(iFontPack *d, const iString *ini) {
331 iBeginCollect(); 339 iBeginCollect();
332 iBool ok = iFalse; 340 iBool ok = iFalse;
333// iFile *f = iClob(new_File(iniPath));
334 //if (open_File(f, text_FileMode | readOnly_FileMode)) {
335// d->loadPath = collect_String(newRange_String(dirName_Path(iniPath)));
336// iString *src = collect_String(readString_File(f));
337 iTomlParser *toml = collect_TomlParser(new_TomlParser()); 341 iTomlParser *toml = collect_TomlParser(new_TomlParser());
338 setHandlers_TomlParser(toml, handleIniTable_FontPack_, handleIniKeyValue_FontPack_, d); 342 setHandlers_TomlParser(toml, handleIniTable_FontPack_, handleIniKeyValue_FontPack_, d);
339 if (parse_TomlParser(toml, ini)) { 343 if (parse_TomlParser(toml, ini)) {
340 ok = iTrue; 344 ok = iTrue;
341 } 345 }
342 iAssert(d->loadSpec == NULL); 346 iAssert(d->loadSpec == NULL);
343// d->loadPath = NULL;
344// }
345 iEndCollect(); 347 iEndCollect();
346 return ok; 348 return ok;
347} 349}
@@ -381,6 +383,7 @@ iBool loadArchive_FontPack(iFontPack *d, const iArchive *zip) {
381 } 383 }
382 deinit_String(&ini); 384 deinit_String(&ini);
383 } 385 }
386 d->archive = NULL;
384 return ok; 387 return ok;
385} 388}
386 389
@@ -423,13 +426,65 @@ void init_Fonts(const char *userDir) {
423 init_PtrArray(&d->specOrder); 426 init_PtrArray(&d->specOrder);
424 /* Load the required fonts. */ { 427 /* Load the required fonts. */ {
425 iFontPack *pack = new_FontPack(); 428 iFontPack *pack = new_FontPack();
426 iArchive *defaultPack = new_Archive(); 429 iArchive *arch = new_Archive();
427 openData_Archive(defaultPack, &fontpackDefault_Embedded); 430 openData_Archive(arch, &fontpackDefault_Embedded);
428 loadArchive_FontPack(pack, defaultPack); 431 loadArchive_FontPack(pack, arch); /* should never fail if we've made it this far */
429 iRelease(defaultPack); 432 iRelease(arch);
430 pushBack_PtrArray(&d->packs, pack); 433 pushBack_PtrArray(&d->packs, pack);
431 } 434 }
432 /* TODO: find and load .fontpack files in known locations */ 435 /* Find and load .fontpack files in known locations. */ {
436 const char *locations[] = {
437 ".",
438 "./fonts",
439 "../share/lagrange",
440 "../../share/lagrange",
441 concatPath_CStr(userDir, "fonts"),
442 userDir,
443 };
444 const iString *execDir = collectNewRange_String(dirName_Path(execPath_App()));
445 iForIndices(i, locations) {
446 const iString *dir = concatCStr_Path(execDir, locations[i]);
447 iForEach(DirFileInfo, entry, iClob(new_DirFileInfo(dir))) {
448 const iString *entryPath = path_FileInfo(entry.value);
449 if (endsWithCase_String(entryPath, ".fontpack")) {
450 iArchive *arch = new_Archive();
451 if (openFile_Archive(arch, entryPath)) {
452 iFontPack *pack = new_FontPack();
453 pack->loadPath = copy_String(entryPath);
454 if (loadArchive_FontPack(pack, arch)) {
455 pushBack_PtrArray(&d->packs, pack);
456 }
457 else {
458 delete_FontPack(pack);
459 fprintf(stderr,
460 "[fonts] errors detected in fontpack: %s\n",
461 cstr_String(entryPath));
462 }
463 }
464 iRelease(arch);
465 }
466 }
467 }
468 }
469 /* A standalone .ini file in the config directory. */ {
470 const iString *userIni = collectNewCStr_String(concatPath_CStr(userDir, "fonts.ini"));
471 iFile *f = new_File(userIni);
472 if (open_File(f, text_FileMode | readOnly_FileMode)) {
473 const iString *src = collect_String(readString_File(f));
474 iFontPack *pack = new_FontPack();
475 pack->loadPath = copy_String(userIni);
476 if (load_FontPack_(pack, src)) {
477 pushBack_PtrArray(&d->packs, pack);
478 }
479 else {
480 delete_FontPack(pack);
481 fprintf(stderr,
482 "[fonts] errors detected in fonts.ini: %s\n",
483 cstr_String(userIni));
484 }
485 }
486 iRelease(f);
487 }
433 sortSpecs_Fonts_(d); 488 sortSpecs_Fonts_(d);
434} 489}
435 490
diff --git a/src/ui/text.c b/src/ui/text.c
index 14b4e305..3ed5b327 100644
--- a/src/ui/text.c
+++ b/src/ui/text.c
@@ -472,7 +472,8 @@ static void deinitFonts_Text_(iText *d) {
472} 472}
473 473
474static int maxGlyphHeight_Text_(const iText *d) { 474static int maxGlyphHeight_Text_(const iText *d) {
475 return 2 * d->contentFontSize * fontSize_UI; 475 /* Huge size is 2 * contentFontSize. */
476 return 4 * d->contentFontSize * fontSize_UI;
476} 477}
477 478
478static void initCache_Text_(iText *d) { 479static void initCache_Text_(iText *d) {
@@ -491,7 +492,7 @@ static void initCache_Text_(iText *d) {
491 /* Allocate initial (empty) rows. These will be assigned actual locations in the cache 492 /* Allocate initial (empty) rows. These will be assigned actual locations in the cache
492 once at least one glyph is stored. */ 493 once at least one glyph is stored. */
493 for (int h = d->cacheRowAllocStep; 494 for (int h = d->cacheRowAllocStep;
494 h <= 2.5 * textSize + d->cacheRowAllocStep; 495 h <= 5 * textSize + d->cacheRowAllocStep;
495 h += d->cacheRowAllocStep) { 496 h += d->cacheRowAllocStep) {
496 pushBack_Array(&d->cacheRows, &(iCacheRow){ .height = 0 }); 497 pushBack_Array(&d->cacheRows, &(iCacheRow){ .height = 0 });
497 } 498 }
diff --git a/src/ui/util.c b/src/ui/util.c
index 73193c7a..0e079efb 100644
--- a/src/ui/util.c
+++ b/src/ui/util.c
@@ -2523,8 +2523,6 @@ iWidget *makePreferences_Widget(void) {
2523 /* Fonts. */ { 2523 /* Fonts. */ {
2524 setId_Widget(appendTwoColumnTabPage_Widget(tabs, "${heading.prefs.fonts}", '4', &headings, &values), "prefs.page.fonts"); 2524 setId_Widget(appendTwoColumnTabPage_Widget(tabs, "${heading.prefs.fonts}", '4', &headings, &values), "prefs.page.fonts");
2525 /* Fonts. */ { 2525 /* Fonts. */ {
2526 addChild_Widget(headings, iClob(makeHeading_Widget("${prefs.font.ui}")));
2527 addFontButtons_(values, "ui");
2528 addChild_Widget(headings, iClob(makeHeading_Widget("${prefs.font.heading}"))); 2526 addChild_Widget(headings, iClob(makeHeading_Widget("${prefs.font.heading}")));
2529 addFontButtons_(values, "heading"); 2527 addFontButtons_(values, "heading");
2530 addChild_Widget(headings, iClob(makeHeading_Widget("${prefs.font.body}"))); 2528 addChild_Widget(headings, iClob(makeHeading_Widget("${prefs.font.body}")));
@@ -2532,41 +2530,44 @@ iWidget *makePreferences_Widget(void) {
2532 addChild_Widget(headings, iClob(makeHeading_Widget("${prefs.font.mono}"))); 2530 addChild_Widget(headings, iClob(makeHeading_Widget("${prefs.font.mono}")));
2533 addFontButtons_(values, "mono"); 2531 addFontButtons_(values, "mono");
2534 addDialogPadding_(headings, values); 2532 addDialogPadding_(headings, values);
2535 addChild_Widget(headings, iClob(makeHeading_Widget("${prefs.mono}"))); 2533 addChild_Widget(headings, iClob(makeHeading_Widget("${prefs.boldlink}")));
2536 iWidget *mono = new_Widget(); { 2534 iWidget *boldLink = new_Widget(); {
2535 /* TODO: Add a utility function for this type of toggles? (also for above) */
2537 iWidget *tog; 2536 iWidget *tog;
2538 setTextCStr_LabelWidget( 2537 setTextCStr_LabelWidget(
2539 addChild_Widget(mono, tog = iClob(makeToggle_Widget("prefs.mono.gemini"))), 2538 addChild_Widget(boldLink, tog = iClob(makeToggle_Widget("prefs.boldlink.dark"))),
2540 "${prefs.mono.gemini}"); 2539 "${prefs.boldlink.dark}");
2541 setFlags_Widget(tog, fixedWidth_WidgetFlag, iFalse); 2540 setFlags_Widget(tog, fixedWidth_WidgetFlag, iFalse);
2542 updateSize_LabelWidget((iLabelWidget *) tog); 2541 updateSize_LabelWidget((iLabelWidget *) tog);
2543 setTextCStr_LabelWidget( 2542 setTextCStr_LabelWidget(
2544 addChild_Widget(mono, tog = iClob(makeToggle_Widget("prefs.mono.gopher"))), 2543 addChild_Widget(boldLink, tog = iClob(makeToggle_Widget("prefs.boldlink.light"))),
2545 "${prefs.mono.gopher}"); 2544 "${prefs.boldlink.light}");
2546 setFlags_Widget(tog, fixedWidth_WidgetFlag, iFalse); 2545 setFlags_Widget(tog, fixedWidth_WidgetFlag, iFalse);
2547 updateSize_LabelWidget((iLabelWidget *) tog); 2546 updateSize_LabelWidget((iLabelWidget *) tog);
2548 } 2547 }
2549 addChildFlags_Widget(values, iClob(mono), arrangeHorizontal_WidgetFlag | arrangeSize_WidgetFlag); 2548 addChildFlags_Widget(values, iClob(boldLink), arrangeHorizontal_WidgetFlag | arrangeSize_WidgetFlag);
2550 addChild_Widget(headings, iClob(makeHeading_Widget("${prefs.font.monodoc}")));
2551 addFontButtons_(values, "monodoc");
2552 addDialogPadding_(headings, values); 2549 addDialogPadding_(headings, values);
2553 addChild_Widget(headings, iClob(makeHeading_Widget("${prefs.boldlink}"))); 2550 addChild_Widget(headings, iClob(makeHeading_Widget("${prefs.mono}")));
2554 iWidget *boldLink = new_Widget(); { 2551 iWidget *mono = new_Widget(); {
2555 /* TODO: Add a utility function for this type of toggles? (also for above) */
2556 iWidget *tog; 2552 iWidget *tog;
2557 setTextCStr_LabelWidget( 2553 setTextCStr_LabelWidget(
2558 addChild_Widget(boldLink, tog = iClob(makeToggle_Widget("prefs.boldlink.dark"))), 2554 addChild_Widget(mono, tog = iClob(makeToggle_Widget("prefs.mono.gemini"))),
2559 "${prefs.boldlink.dark}"); 2555 "${prefs.mono.gemini}");
2560 setFlags_Widget(tog, fixedWidth_WidgetFlag, iFalse); 2556 setFlags_Widget(tog, fixedWidth_WidgetFlag, iFalse);
2561 updateSize_LabelWidget((iLabelWidget *) tog); 2557 updateSize_LabelWidget((iLabelWidget *) tog);
2562 setTextCStr_LabelWidget( 2558 setTextCStr_LabelWidget(
2563 addChild_Widget(boldLink, tog = iClob(makeToggle_Widget("prefs.boldlink.light"))), 2559 addChild_Widget(mono, tog = iClob(makeToggle_Widget("prefs.mono.gopher"))),
2564 "${prefs.boldlink.light}"); 2560 "${prefs.mono.gopher}");
2565 setFlags_Widget(tog, fixedWidth_WidgetFlag, iFalse); 2561 setFlags_Widget(tog, fixedWidth_WidgetFlag, iFalse);
2566 updateSize_LabelWidget((iLabelWidget *) tog); 2562 updateSize_LabelWidget((iLabelWidget *) tog);
2567 } 2563 }
2568 addChildFlags_Widget(values, iClob(boldLink), arrangeHorizontal_WidgetFlag | arrangeSize_WidgetFlag); 2564 addChildFlags_Widget(values, iClob(mono), arrangeHorizontal_WidgetFlag | arrangeSize_WidgetFlag);
2565 addChild_Widget(headings, iClob(makeHeading_Widget("${prefs.font.monodoc}")));
2566 addFontButtons_(values, "monodoc");
2569 addDialogPadding_(headings, values); 2567 addDialogPadding_(headings, values);
2568 addChild_Widget(headings, iClob(makeHeading_Widget("${prefs.font.ui}")));
2569 addFontButtons_(values, "ui");
2570 // addDialogPadding_(headings, values);
2570// /* Custom font. */ { 2571// /* Custom font. */ {
2571// iInputWidget *customFont = new_InputWidget(0); 2572// iInputWidget *customFont = new_InputWidget(0);
2572// setHint_InputWidget(customFont, "${hint.prefs.userfont}"); 2573// setHint_InputWidget(customFont, "${hint.prefs.userfont}");