axui-growth-chamber/src/ctxt/ctxt.c

145 lines
4.0 KiB
C

#include "../ctxt.h"
#include "../util.h"
#include "../ax.h"
#include "theme.h"
/* -----------------------------------------------------------------------------
* API functions :: init / cleanup
* -------------------------------------------------------------------------- */
struct ax_ctxt* ax_new(void)
{
// "bootstrap" a new region
struct rgn rgn0;
rgn_init(&rgn0, SMALL);
struct rgn* rgn = rmemdup_typed(&rgn0, struct rgn, &rgn0, 1);
// use it to make a new context
struct ax_ctxt* ax = ralloc_typed(rgn, struct ax_ctxt, 1);
ax__ctxt_init(ax, rgn);
return ax;
}
void ax_free(struct ax_ctxt* ax)
{
ax__ctxt_cleanup(ax);
rgn_cleanup(ax->init_rgn);
}
const char* ax_get_error(struct ax_ctxt* ax)
{
return ax->err;
}
/* -----------------------------------------------------------------------------
* Internal 'ax_ctxt' operations
* -------------------------------------------------------------------------- */
void ax__ctxt_init(struct ax_ctxt* ax, struct rgn* init_rgn)
{
ax->init_rgn = init_rgn;
ax->log_out = NULL;
ax->log_auto_close = false;
rgn_init(&ax->err_rgn, SMALL);
ax->err = "";
rgn_init(&ax->thmb_rgn, THEME_BUILDER_DESIRED_REGION_SIZE);
ax->thmb = NULL;
ax->sel_theme = NULL;
}
void ax__ctxt_cleanup(struct ax_ctxt* ax)
{
rgn_cleanup(&ax->thmb_rgn);
rgn_cleanup(&ax->err_rgn);
}
/* -----------------------------------------------------------------------------
* API functions :: logging
* -------------------------------------------------------------------------- */
void ax_set_logger(struct ax_ctxt* ax, int fd, bool auto_close)
{
if (ax->log_auto_close) {
fclose(ax->log_out);
}
ax->log_out = fdopen(fd, "w");
ax->log_auto_close = auto_close;
}
void ax_log(struct ax_ctxt* ax, const char* string)
{
if (ax->log_out != NULL) {
fprintf(ax->log_out, "[LOG] %s\n", string);
}
}
/* -----------------------------------------------------------------------------
* API functions :: themes
* -------------------------------------------------------------------------- */
void ax_begin_theme(struct ax_ctxt* ax)
{
rgn_clear(&ax->thmb_rgn);
ax->thmb = ralloc_typed(&ax->thmb_rgn, struct ax_theme_builder, 1);
ax__theme_builder_init(ax->thmb, &ax->thmb_rgn);
}
void ax_end_theme(struct ax_ctxt* ax, struct ax_theme** out_thm)
{
ASSERT(ax->thmb != NULL, "`ax_end_theme' called while not building a theme");
ax__theme_builder_finish(ax->thmb, ax->init_rgn, out_thm);
rgn_clear(&ax->thmb_rgn);
}
void ax_set_theme_color(
struct ax_ctxt* ax, const char* cat_name, int64_t rgb)
{
ASSERT(ax->thmb != NULL, "`ax_set_theme_color' called while not building a theme");
enum ax_color_cat cat;
if (ax__string_to_color_cat(cat_name, &cat) != 0) {
#define FMT "invalid color category `%s'"
sprintf(ax__theme_make_error_buf(ax->thmb, strlen(FMT) + strlen(cat_name)),
FMT, cat_name);
#undef FMT
} else {
ax__theme_set_color(ax->thmb, cat, rgb);
}
}
void ax_set_theme_font(
struct ax_ctxt* ax, const char* cat_name, const char* fnt_path, size_t fnt_size)
{
ASSERT(ax->thmb != NULL, "`ax_set_theme_font' called while not building a theme");
enum ax_font_cat cat;
if (ax__string_to_font_cat(cat_name, &cat) != 0) {
#define FMT "invalid font category `%s'"
sprintf(ax__theme_make_error_buf(ax->thmb, strlen(FMT) + strlen(cat_name)),
FMT, cat_name);
#undef FMT
} else {
ax__theme_set_font(ax->thmb, cat, fnt_path, fnt_size);
}
}
void ax_set_theme_iconset(
struct ax_ctxt* ax, const char* iconset_dir)
{
ASSERT(ax->thmb != NULL, "`ax_set_theme_iconset' called while not building a theme");
UNIMPLEMENTED();
}
int ax_select_theme(struct ax_ctxt* ax, struct ax_theme* thm)
{
ASSERT_NON_NULL(thm, "theme");
if (thm->fatal_err != NULL) {
ax->err = thm->fatal_err;
return AX_ERR_THEME_INVALID;
}
// TODO: see if font is loaded
ax->sel_theme = thm;
ax_log(ax, "theme selected");
return 0;
}