#include "hershey_fonts.hpp" #include "common/unicode_sorta.hpp" #include namespace hershey { std::map fonts = { { "sans", &futural }, //{ "sans_bold", &futuram }, { "gothic", &gothgbt }, //{ "cursive_bold", &scriptc }, { "cursive", &scripts }, { "serif_italic", ×i }, { "serif", ×r }, //{ "serif_bold", ×rb } }; inline float deg2rad(float degrees) { return (degrees * M_PI) / 180.0f; } const font_glyph_t* glyph_data(const font_t* font, unsigned char c) { if(c < 32 || c > 127 + 64) { // + 64 char remappings defined in unicode_sorta.hpp return nullptr; } if(c > 127) { c = unicode_sorta::char_base[c - 128]; } return &font->chars[c - 32]; } int32_t measure_glyph(const font_t* font, unsigned char c, float s) { const font_glyph_t *gd = glyph_data(font, c); // if glyph data not found (id too great) then skip if(!gd) { return 0; } return gd->width * s; } int32_t measure_text(const font_t* font, std::string message, float s) { int32_t width = 0; for(auto &c : message) { width += measure_glyph(font, c, s); } return width; } int32_t glyph(const font_t* font, line_func line, unsigned char c, int32_t x, int32_t y, float s, float a) { const font_glyph_t *gd = glyph_data(font, c); // if glyph data not found (id too great) then skip if(!gd) { return 0; } a = deg2rad(a); float as = sin(a); float ac = cos(a); const int8_t *pv = gd->vertices; int8_t cx = (*pv++) * s; int8_t cy = (*pv++) * s; bool pen_down = true; for(uint32_t i = 1; i < gd->vertex_count; i++) { if(pv[0] == -128 && pv[1] == -128) { pen_down = false; pv += 2; }else{ int8_t nx = (*pv++) * s; int8_t ny = (*pv++) * s; int rcx = (cx * ac - cy * as) + 0.5f; int rcy = (cx * as + cy * ac) + 0.5f; int rnx = (nx * ac - ny * as) + 0.5f; int rny = (nx * as + ny * ac) + 0.5f; if(pen_down) { line(rcx + x, rcy + y, rnx + x, rny + y); } cx = nx; cy = ny; pen_down = true; } } return gd->width * s; } void text(const font_t* font, line_func line, std::string message, int32_t x, int32_t y, float s, float a) { int32_t cx = x; int32_t cy = y; int32_t ox = 0; float as = sin(deg2rad(a)); float ac = cos(deg2rad(a)); for(auto &c : message) { int rcx = (ox * ac) + 0.5f; int rcy = (ox * as) + 0.5f; ox += glyph(font, line, c, cx + rcx, cy + rcy, s, a); } } }