release: Hermit 1.0.0 — home layout, icon font, install
ci / tcc-check (push) Failing after 41s
ci / linux (aarch64, 0) (push) Skipped
ci / linux (x86, 1) (push) Skipped
ci / linux (x86_64, 1) (push) Skipped
ci / windows (push) Skipped

Compact the home parliament chip, animate crab states like the HTML kit,
ship hermit-icons.ttf (sbix) + frames, and install the font from make/
bootstrap/package paths.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
WHC
2026-10-29 21:57:46 +08:00
co-authored by Cursor
parent 8fcbd886c3
commit 41f4cf85ee
109 changed files with 472 additions and 218 deletions
+52 -22
View File
@@ -2721,6 +2721,8 @@ static int hermit_role_pair(int role) {
return COLORS >= 256 ? CP_MUTED : CP_ERROR; /* brick legs */
case 4:
return CP_SGR_CYAN; /* >_ */
case 5:
return CP_ASSIST; /* ? ! claw mark */
default:
return CP_MUTED;
}
@@ -2743,15 +2745,31 @@ static void draw_hermit_icon(WINDOW *win, int y0, int x0, hermit_state_t st,
}
}
const char *lines[8];
int n = hermit_shell_art(st, with_shell, g_ascii, lines, 8);
int n = hermit_shell_art_frame(st, with_shell, g_ascii, frame, lines, 8);
for (int r = 0; r < n; r++) {
const char *row = lines[r];
for (int c = 0; row[c]; c++) {
if (row[c] == ' ')
char raw = row[c];
if (raw == ' ')
continue;
char ch[2] = {row[c], 0};
int pair = hermit_role_pair(hermit_shell_cell_role(st, with_shell, r, c));
draw_ansi_at(win, y0 + r, x0 + c, 1, ch, pair, 0, 0);
char draw = (raw == '@') ? '#' : raw;
int role = 0;
if (raw == '@')
role = 1;
else if (raw == '#' )
role = (with_shell && r <= 2) ? 1 : 0;
else if (raw == '>' || raw == '_')
role = 4;
else if (raw == ':' || raw == '=' || raw == '^' || raw == 'x')
role = 2;
else if (raw == '|')
role = 3;
else if (raw == '?' || raw == '!' || raw == '~')
role = 5;
else
role = hermit_shell_cell_role(st, with_shell, r, c);
char ch[2] = {draw, 0};
draw_ansi_at(win, y0 + r, x0 + c, 1, ch, hermit_role_pair(role), 0, 0);
}
}
}
@@ -2804,10 +2822,12 @@ static void draw_home(tui_t *t) {
const char *lb = hermit_getenv("LOGO");
want_block = lb[0] && !strcmp(lb, "block");
}
/* Crab on the right of the brand stack when there is room. */
int crab_w = 14, crab_h = 6;
hermit_state_t crab_st = hermit_state_from_ui(
t->busy, t->ask_pending || t->awaiting_perm, 0);
int crab_w = hermit_shell_art_width();
int crab_h = hermit_shell_art_height();
int crab_x = w - crab_w - 2;
int show_crab = crab_x > LOGO_W + 4 && box_top >= crab_h + 1;
int show_crab = crab_x > 20 && box_top >= crab_h + 1 && w >= 48;
if (want_block && !(g_ascii || !g_utf8 || g_logo_text) &&
box_top - LOGO_H - 2 >= 0 && w >= LOGO_W) {
int x0 = show_crab ? (crab_x - LOGO_W) / 2 : (w - LOGO_W) / 2;
@@ -2822,7 +2842,7 @@ static void draw_home(tui_t *t) {
} else {
const char *mark = "HERMIT";
int mw = (int)strlen(mark);
int x = show_crab ? (crab_x - mw) / 2 : (w - mw) / 2;
int x = (w - mw) / 2;
if (x < 0)
x = 0;
if (brand_y >= 1)
@@ -2830,32 +2850,42 @@ static void draw_home(tui_t *t) {
draw_ansi_at(t->logw, brand_y, x, mw, mark, CP_ACCENT, 1, 0);
}
if (show_crab) {
int cy = box_top - crab_h;
int cy = brand_y;
if (cy + crab_h > box_top)
cy = box_top - crab_h;
if (cy < 0)
cy = 0;
draw_hermit_icon(t->logw, cy, crab_x, HERMIT_ST_IDLE, 1, t->spin);
draw_hermit_icon(t->logw, cy, crab_x, crab_st, 1, t->spin);
}
int ty = brand_y + 1;
if (ty < box_top) {
const char *tag =
g_ascii ? "code . plan . parliament" : "code · plan · parliament";
int tw = (int)strlen(tag);
int x = show_crab ? (crab_x - tw) / 2 : (w - tw) / 2;
int x = (w - tw) / 2;
if (x < 0)
x = 0;
draw_ansi_at(t->logw, ty, x, tw, tag, CP_MUTED, 0, 0);
}
/* Compact parliament chip — never dump full status_text on the home. */
if (cst_parliament_is_active() && ty + 1 < box_top) {
char *st = cst_parliament_status_text();
if (st && st[0]) {
char chip[160];
snprintf(chip, sizeof(chip), "%s %s", g_ascii ? "*" : "◆", st);
int cw = vis_cols(chip);
if (cw > w - 2)
cw = w - 2;
draw_ansi_at(t->logw, ty + 1, (w - cw) / 2, cw, chip, CP_ACCENT, 0, 0);
}
free(st);
cst_parliament_meta_t m;
memset(&m, 0, sizeof(m));
cst_parliament_load(&m);
char sid[64] = {0};
int sess = cst_parliament_session_ok(sid, sizeof(sid));
int chair = sess && cst_parliament_is_chair();
char chip[96];
snprintf(chip, sizeof(chip), "%s parliament · rev=%lu · %s",
g_ascii ? "*" : "◆", (unsigned long)m.revision,
!sess ? "login" : chair ? "chair" : "member");
int cw = vis_cols(chip);
if (cw > w - 4)
cw = w - 4;
int cx = (w - cw) / 2;
if (cx < 0)
cx = 0;
draw_ansi_at(t->logw, ty + 1, cx, cw, chip, CP_ACCENT, 0, 0);
}
int right = t->in_x - t->log_x + t->in_w;
if (box_bot < h) {