Progress Bar Widget¶
The Progress Bar is a filled-track indicator — a percentage readout, a
fuel gauge, a system-status meter. Init installs theme-tracked fill/track/
border colours, a default border width and corner radius, and (with
UGUI_ENABLE_DEFAULTS) a visible default size. set_value() moves the
fill; set_range() remaps the scale away from a raw 0..100 percentage;
set_orient() switches between horizontal and vertical fill growth; and an
optional set_text() overlay renders a centred label on top of the fill,
two-tone so it stays legible over both the filled and empty regions.
Every example below is complete — the file-scope storage, the callbacks and
the build calls — beside the exact frame it renders on a 480×320 panel. Each
compiles against nothing but the released library: drop it into the
Application Skeleton and it runs as-is. The icons come from
inc/icons/, the lexend fonts from inc/fonts/ — both ship with the library.
Examples¶
Default Bar¶
A bar created with nothing but ugui_widget_progress_init() — theme colours, default border/radius/size, all from the library. set_text() attaches the built-in percentage overlay; a "Bump +10%" button drives set_value() to show the fill (and its own overlay text) updating live.

/* --- widget IDs: only need to be unique within the screen (10+ leaves
* room for the IDs your app already uses, e.g. the root's) --- */
enum {
WDGT_ID_DEMO = 10, WDGT_ID_TRIGGER
};
/* --- fonts: each is DEFINED in inc/fonts/<name>.h — #include that
* header in exactly one .c of your app; elsewhere just: --- */
extern const ugui_font_t lexend_14pt_2bpp;
/* --- file-scope storage --- */
#if defined(UGUI_WIDGET_ENABLE_PROGRESS_BAR)
static ugui_screen_t s_screen;
static ugui_widget_t s_root;
static ugui_widget_t s_bar;
static ugui_progress_bar_ext_t s_bar_ext;
static ugui_widget_t s_trigger;
static ugui_button_ext_t s_trigger_ext;
#endif
#if defined(UGUI_WIDGET_ENABLE_PROGRESS_BAR)
static ugui_text_cfg_t s_bar_text;
static char s_bar_buf[12]; /* e.g. "65 %" */
static ugui_text_cfg_t s_trigger_text;
#endif
#if defined(UGUI_WIDGET_ENABLE_PROGRESS_BAR)
#define TRIGGER_W 180
#define TRIGGER_H 36
#define TRIGGER_X ((int16_t)((UGUI_SCREEN_W - TRIGGER_W) / 2))
#define TRIGGER_Y ((int16_t)((UGUI_SCREEN_H / 2) + 30))
#endif
/* --- local helpers & event callbacks --- */
static void update_label(void)
{
#ifdef UGUI_ENABLE_FONT
int16_t v = ugui_widget_progress_get_value(&s_bar);
(void)snprintf(s_bar_buf, sizeof(s_bar_buf), "%d %%", (int)v);
s_bar_text.str = s_bar_buf;
ugui_widget_invalidate(&s_bar);
#endif
}
static void on_bump(uint8_t widget_id, ugui_event_t event)
{
(void)widget_id;
if (event != UGUI_EVENT_CLICK) { return; }
int16_t v = ugui_widget_progress_get_value(&s_bar);
v = (int16_t)(v + 10);
if (v > 100) { v = 0; } /* wrap back to empty after reaching full */
ugui_widget_progress_set_value(&s_bar, v);
update_label();
}
static void add_button(ugui_widget_t* w, ugui_button_ext_t* ext, ugui_text_cfg_t* text,
uint8_t id, int16_t x, int16_t y, int16_t bw, int16_t bh,
const char* str, ugui_event_cb_t cb)
{
ugui_widget_button_init(&s_root, w, ext);
ugui_widget_set_area(w, x, y, bw, bh);
ugui_widget_set_id(w, id);
ugui_widget_button_set_style(w, true, 5u, 1u, UGUI_THEME_SURFACE, UGUI_THEME_ACCENT);
#ifdef UGUI_ENABLE_FONT
ugui_text_cfg_init(text, str, &lexend_14pt_2bpp, UGUI_THEME_TEXT,
UGUI_ALIGN_CENTER, (ugui_point_t){ 0, 0 }, 1u);
ugui_widget_button_set_text(w, text);
#endif
ugui_widget_set_event_cb(w, cb,
UGUI_EMASK_CLICK | UGUI_EMASK_DOWN | UGUI_EMASK_UP
| UGUI_EMASK_KEY_CONFIRM);
ugui_screen_add_widget(&s_screen, w);
#if UGUI_ENABLE_KEYPAD
ugui_screen_add_focus(&s_screen, w);
#endif
}
/* --- build it (in your screen's init) --- */
ugui_widget_progress_init(&s_root, &s_bar, &s_bar_ext);
ugui_widget_set_align(&s_bar, UGUI_ALIGN_CENTER, 0, -20);
ugui_widget_set_id(&s_bar, WDGT_ID_DEMO);
ugui_widget_progress_set_value(&s_bar, 40);
#ifdef UGUI_ENABLE_FONT
ugui_text_cfg_init(&s_bar_text, s_bar_buf, &lexend_14pt_2bpp, UGUI_THEME_KNOB,
UGUI_ALIGN_CENTER, (ugui_point_t){ 0, 0 }, 1u);
ugui_widget_progress_set_text(&s_bar, &s_bar_text);
#endif
ugui_screen_add_widget(&s_screen, &s_bar);
update_label();
add_button(&s_trigger, &s_trigger_ext, &s_trigger_text, WDGT_ID_TRIGGER,
TRIGGER_X, TRIGGER_Y, TRIGGER_W, TRIGGER_H, "Bump +10%", on_bump);
Value Coverage & Orientation¶
Three horizontal bars pinned at the extremes and the midpoint — the three shapes a fill region can take. Beside them, the same kind of bar with set_orient(UGUI_PBAR_VERT) (fill grows bottom-up) and a remapped set_range(0, 200) — a "fuel: 0..200 L" reading instead of a raw percentage, showing the widget isn't tied to 0..100.

/* --- widget IDs: only need to be unique within the screen (10+ leaves
* room for the IDs your app already uses, e.g. the root's) --- */
enum {
WDGT_ID_SLOT0 = 10, WDGT_ID_SLOT4, WDGT_ID_SLOT7,
WDGT_ID_SLOT8
};
/* --- fonts: each is DEFINED in inc/fonts/<name>.h — #include that
* header in exactly one .c of your app; elsewhere just: --- */
extern const ugui_font_t lexend_14pt_2bpp;
/* --- file-scope storage --- */
#if defined(UGUI_WIDGET_ENABLE_PROGRESS_BAR)
static ugui_screen_t s_screen;
static ugui_widget_t s_root;
#define ROW_N 3u
static ugui_widget_t s_row_w [ROW_N];
static ugui_progress_bar_ext_t s_row_ext[ROW_N];
static ugui_widget_t s_row_lbl[ROW_N];
static ugui_label_ext_t s_row_lbl_ext[ROW_N];
static const char* const k_row_label[ROW_N] = { "Empty (0%)", "Half (50%)", "Full (100%)" };
static const int16_t k_row_value[ROW_N] = { 0, 50, 100 };
static ugui_widget_t s_vert_w;
static ugui_progress_bar_ext_t s_vert_ext;
static ugui_widget_t s_vert_val;
static ugui_label_ext_t s_vert_val_ext;
#endif
#if defined(UGUI_WIDGET_ENABLE_PROGRESS_BAR)
static char s_vert_buf[16];
#endif
#if defined(UGUI_WIDGET_ENABLE_PROGRESS_BAR)
#define ROW_X 10
#define ROW_W 260
#define LBL_H 18
#define BAR_H 28
#define ROW_STEP 56
#define ROW0_Y 48
#define VCOL_X ((int16_t)(ROW_X + ROW_W + 40))
#define VCOL_W 44
#define VCOL_LBL_Y ROW0_Y
#define VCOL_BAR_Y ((int16_t)(VCOL_LBL_Y + LBL_H + 4))
#define VCOL_BAR_H 170
#define VCOL_VAL_Y ((int16_t)(VCOL_BAR_Y + VCOL_BAR_H + 6))
#endif
/* --- local helpers & event callbacks --- */
static void add_label(ugui_widget_t* w, ugui_label_ext_t* ext, uint8_t id,
int16_t x, int16_t y, int16_t cw, int16_t ch,
const char* str, ugui_align_t align)
{
ugui_widget_label_init(&s_root, w, ext);
ugui_widget_set_area(w, x, y, cw, ch);
ugui_widget_set_id (w, id);
ugui_widget_label_set_style(w, /*bg_fill=*/false, UGUI_THEME_BG, str,
&lexend_14pt_2bpp, UGUI_THEME_TEXT, align, 1u);
ugui_screen_add_widget(&s_screen, w);
}
/* --- build it (in your screen's init) --- */
uint8_t i;
for (i = 0u; i < ROW_N; i++) {
int16_t lbl_y = (int16_t)(ROW0_Y + (int16_t)i * ROW_STEP);
int16_t bar_y = (int16_t)(lbl_y + LBL_H);
add_label(&s_row_lbl[i], &s_row_lbl_ext[i], (uint8_t)(WDGT_ID_SLOT0 + i),
ROW_X, lbl_y, ROW_W, LBL_H, k_row_label[i], UGUI_ALIGN_LEFT);
ugui_widget_progress_init(&s_root, &s_row_w[i], &s_row_ext[i]);
ugui_widget_set_area(&s_row_w[i], ROW_X, bar_y, ROW_W, BAR_H);
ugui_widget_set_id(&s_row_w[i], (uint8_t)(WDGT_ID_SLOT4 + i));
ugui_widget_progress_set_value(&s_row_w[i], k_row_value[i]);
ugui_screen_add_widget(&s_screen, &s_row_w[i]);
}
ugui_widget_progress_init(&s_root, &s_vert_w, &s_vert_ext);
ugui_widget_set_area(&s_vert_w, VCOL_X, VCOL_BAR_Y, VCOL_W, VCOL_BAR_H);
ugui_widget_set_id(&s_vert_w, WDGT_ID_SLOT7);
ugui_widget_progress_set_orient(&s_vert_w, UGUI_PBAR_VERT);
ugui_widget_progress_set_range(&s_vert_w, 0, 200);
ugui_widget_progress_set_value(&s_vert_w, 130);
ugui_screen_add_widget(&s_screen, &s_vert_w);
/* Readout: get_value() reflected back as text under the bar. */
#ifdef UGUI_ENABLE_FONT
(void)snprintf(s_vert_buf, sizeof(s_vert_buf), "%d L", (int)ugui_widget_progress_get_value(&s_vert_w));
#endif
add_label(&s_vert_val, &s_vert_val_ext, WDGT_ID_SLOT8,
(int16_t)(VCOL_X - 20), VCOL_VAL_Y, 90, 20,
#ifdef UGUI_ENABLE_FONT
s_vert_buf,
#else
"130 L",
#endif
UGUI_ALIGN_LEFT);
Colours, Sizes & Text Overlay¶
A colour column (four set_colors() presets), a size column (the same bar at three border/radius/height combos — plain ext fields, no dedicated setter), and a label demo turning on the built-in centred percentage overlay via set_text().

/* --- widget IDs: only need to be unique within the screen (10+ leaves
* room for the IDs your app already uses, e.g. the root's) --- */
enum {
WDGT_ID_SLOT0 = 10, WDGT_ID_SLOT8, WDGT_ID_SLOT17
};
/* --- fonts: each is DEFINED in inc/fonts/<name>.h — #include that
* header in exactly one .c of your app; elsewhere just: --- */
extern const ugui_font_t lexend_14pt_2bpp;
/* --- file-scope storage --- */
#if defined(UGUI_WIDGET_ENABLE_PROGRESS_BAR)
static ugui_screen_t s_screen;
static ugui_widget_t s_root;
#define COL_N 4u
static ugui_widget_t s_col_w [COL_N];
static ugui_progress_bar_ext_t s_col_ext[COL_N];
static ugui_widget_t s_col_lbl[COL_N];
static ugui_label_ext_t s_col_lbl_ext[COL_N];
static const char* const k_col_name[COL_N] = { "Accent", "Success", "Caution", "Alert" };
#define SIZE_N 3u
static ugui_widget_t s_size_w [SIZE_N];
static ugui_progress_bar_ext_t s_size_ext[SIZE_N];
static ugui_widget_t s_size_lbl[SIZE_N];
static ugui_label_ext_t s_size_lbl_ext[SIZE_N];
static const char* const k_size_name [SIZE_N] = { "Small", "Medium", "Large" };
static const uint8_t k_size_border[SIZE_N] = { 1u, 2u, 3u };
static const uint8_t k_size_radius[SIZE_N] = { 2u, 4u, 8u };
static const int16_t k_size_h [SIZE_N] = { 14, 22, 32 };
static ugui_widget_t s_lbl_w;
static ugui_progress_bar_ext_t s_lbl_ext;
#endif
#if defined(UGUI_WIDGET_ENABLE_PROGRESS_BAR)
static ugui_text_cfg_t s_lbl_text;
#endif
#if defined(UGUI_WIDGET_ENABLE_PROGRESS_BAR)
#define HDR_Y 38
#define COL_LBL_X 10
#define COL_LBL_W 74
#define COL_BAR_X ((int16_t)(COL_LBL_X + COL_LBL_W + 4))
#define COL_BAR_W 120
#define COL_BAR_H 22
#define COL_ROW0 ((int16_t)(HDR_Y + 24))
#define COL_STEP 32
#define SIZE_LBL_X ((int16_t)(COL_BAR_X + COL_BAR_W + 30))
#define SIZE_LBL_W 62
#define SIZE_BAR_X ((int16_t)(SIZE_LBL_X + SIZE_LBL_W + 4))
#define SIZE_BAR_W 140
#define LBL_DEMO_Y 220
#define LBL_DEMO_BAR_Y ((int16_t)(LBL_DEMO_Y + 22))
#define LBL_DEMO_W ((int16_t)(UGUI_SCREEN_W - 2 * 10))
#define LBL_DEMO_H 30
#endif
/* --- local helpers & event callbacks --- */
static void add_label(ugui_widget_t* w, ugui_label_ext_t* ext, uint8_t id,
int16_t x, int16_t y, int16_t cw, int16_t ch,
const char* str, ugui_align_t align)
{
ugui_widget_label_init(&s_root, w, ext);
ugui_widget_set_area(w, x, y, cw, ch);
ugui_widget_set_id (w, id);
ugui_widget_label_set_style(w, /*bg_fill=*/false, UGUI_THEME_BG, str,
&lexend_14pt_2bpp, UGUI_THEME_TEXT, align, 1u);
ugui_screen_add_widget(&s_screen, w);
}
/* --- build it (in your screen's init) --- */
ugui_color_t fill_col[COL_N];
fill_col[0] = UGUI_THEME_ACCENT;
fill_col[1] = UGUI_THEME_OK;
fill_col[2] = ugui_color_preset_caution();
fill_col[3] = UGUI_THEME_CANCEL;
uint8_t i;
for (i = 0u; i < COL_N; i++) {
int16_t row_y = (int16_t)(COL_ROW0 + (int16_t)i * COL_STEP);
add_label(&s_col_lbl[i], &s_col_lbl_ext[i], (uint8_t)(WDGT_ID_SLOT0 + i),
COL_LBL_X, row_y, COL_LBL_W, COL_BAR_H, k_col_name[i],
(ugui_align_t)(UGUI_ALIGN_LEFT | UGUI_ALIGN_V_CENTER));
ugui_widget_progress_init(&s_root, &s_col_w[i], &s_col_ext[i]);
ugui_widget_set_area(&s_col_w[i], COL_BAR_X, row_y, COL_BAR_W, COL_BAR_H);
ugui_widget_progress_set_colors(&s_col_w[i], fill_col[i], UGUI_THEME_SURFACE, UGUI_THEME_ACCENT);
ugui_widget_progress_set_value(&s_col_w[i], 65);
ugui_screen_add_widget(&s_screen, &s_col_w[i]);
}
int16_t size_y = COL_ROW0;
for (i = 0u; i < SIZE_N; i++) {
int16_t row_h = k_size_h[i];
add_label(&s_size_lbl[i], &s_size_lbl_ext[i], (uint8_t)(WDGT_ID_SLOT8 + i),
SIZE_LBL_X, size_y, SIZE_LBL_W, row_h, k_size_name[i],
(ugui_align_t)(UGUI_ALIGN_LEFT | UGUI_ALIGN_V_CENTER));
ugui_widget_progress_init(&s_root, &s_size_w[i], &s_size_ext[i]);
ugui_widget_set_area(&s_size_w[i], SIZE_BAR_X, size_y, SIZE_BAR_W, row_h);
s_size_ext[i].border_width = k_size_border[i];
s_size_ext[i].corner_radius = k_size_radius[i];
ugui_widget_progress_set_value(&s_size_w[i], 55);
ugui_screen_add_widget(&s_screen, &s_size_w[i]);
size_y = (int16_t)(size_y + row_h + 10);
}
ugui_widget_progress_init(&s_root, &s_lbl_w, &s_lbl_ext);
ugui_widget_set_area(&s_lbl_w, 10, LBL_DEMO_BAR_Y, LBL_DEMO_W, LBL_DEMO_H);
ugui_widget_set_id(&s_lbl_w, WDGT_ID_SLOT17);
ugui_widget_progress_set_value(&s_lbl_w, 42);
#ifdef UGUI_ENABLE_FONT
ugui_text_cfg_init(&s_lbl_text, "42 %", &lexend_14pt_2bpp, UGUI_THEME_KNOB,
UGUI_ALIGN_CENTER, (ugui_point_t){ 0, 0 }, 1u);
ugui_widget_progress_set_text(&s_lbl_w, &s_lbl_text);
#endif
ugui_screen_add_widget(&s_screen, &s_lbl_w);
System Status Panel¶
A realistic dashboard: four bars re-coloured by set_colors() from a shared green/amber/red threshold function, each carrying its own live percentage overlay. "Randomize" redraws every row with a new value (and usually a new colour band), proving set_value() + set_colors() + the text overlay all update together on every press.

/* --- widget IDs: only need to be unique within the screen (10+ leaves
* room for the IDs your app already uses, e.g. the root's) --- */
enum {
WDGT_ID_SLOT4 = 10, WDGT_ID_SLOT0, WDGT_ID_RANDOMIZE
};
/* --- fonts: each is DEFINED in inc/fonts/<name>.h — #include that
* header in exactly one .c of your app; elsewhere just: --- */
extern const ugui_font_t lexend_14pt_2bpp;
/* --- file-scope storage --- */
#if defined(UGUI_WIDGET_ENABLE_PROGRESS_BAR)
static ugui_screen_t s_screen;
static ugui_widget_t s_root;
#define ROW_N 4u
static ugui_widget_t s_bar_w [ROW_N];
static ugui_progress_bar_ext_t s_bar_ext[ROW_N];
static ugui_widget_t s_label [ROW_N];
static ugui_label_ext_t s_label_ext[ROW_N];
static ugui_widget_t s_randomize_btn;
static ugui_button_ext_t s_randomize_ext;
#endif
#if defined(UGUI_WIDGET_ENABLE_PROGRESS_BAR)
static ugui_text_cfg_t s_bar_text[ROW_N];
static char s_bar_buf [ROW_N][12];
static ugui_text_cfg_t s_randomize_text;
#endif
#if defined(UGUI_WIDGET_ENABLE_PROGRESS_BAR)
static const char* const k_row_label [ROW_N] = { "CPU", "Memory", "Disk", "Battery" };
static const int16_t k_row_init [ROW_N] = { 42, 78, 91, 15 };
static const uint8_t k_row_invert[ROW_N] = { 0u, 0u, 0u, 1u };
#define BTN_H 32
#define BTN_Y ((int16_t)(UGUI_SCREEN_H - BTN_H - 10))
#define PANEL_X 10
#define PANEL_Y ((int16_t)(38 + 4))
#define PANEL_W ((int16_t)(UGUI_SCREEN_W - 2 * 10))
#define PANEL_H ((int16_t)(BTN_Y - PANEL_Y - 8))
#define ROW_STEP ((int16_t)(PANEL_H / (int16_t)ROW_N))
#define BAR_H 26
#define LBL_X ((int16_t)(PANEL_X + 12))
#define LBL_W 90
#define BAR_X ((int16_t)(LBL_X + LBL_W + 8))
#define BAR_W ((int16_t)(PANEL_X + PANEL_W - BAR_X - 12))
static uint32_t s_rng_state = 0x2026u;
#endif
/* --- local helpers & event callbacks --- */
static uint32_t next_rand(void)
{
uint32_t x = s_rng_state;
x ^= (uint32_t)(x << 13);
x ^= (x >> 17);
x ^= (uint32_t)(x << 5);
s_rng_state = x;
return x;
}
static ugui_color_t threshold_color(int16_t pct, uint8_t invert)
{
int16_t bad_hi = invert ? 15 : 85; /* Battery: <=15% is critical */
int16_t warn_hi = invert ? 40 : 60; /* Battery: <=40% is low */
if (invert != 0u) {
if (pct <= bad_hi) { return UGUI_THEME_CANCEL; } /* red */
if (pct <= warn_hi) { return ugui_color_preset_caution(); } /* amber */
return UGUI_THEME_OK; /* green */
}
if (pct >= bad_hi) { return UGUI_THEME_CANCEL; } /* red */
if (pct >= warn_hi) { return ugui_color_preset_caution(); } /* amber */
return UGUI_THEME_OK; /* green */
}
static void apply_row(uint8_t i, int16_t pct)
{
ugui_widget_progress_set_value(&s_bar_w[i], pct);
ugui_widget_progress_set_colors(&s_bar_w[i], threshold_color(pct, k_row_invert[i]),
UGUI_THEME_SURFACE, UGUI_THEME_ACCENT);
#ifdef UGUI_ENABLE_FONT
(void)snprintf(s_bar_buf[i], sizeof(s_bar_buf[i]), "%d %%", (int)pct);
s_bar_text[i].str = s_bar_buf[i];
ugui_widget_invalidate(&s_bar_w[i]);
#endif
}
static void on_randomize(uint8_t widget_id, ugui_event_t event)
{
(void)widget_id;
if (event != UGUI_EVENT_CLICK) { return; }
uint8_t i;
for (i = 0u; i < ROW_N; i++) {
int16_t pct = (int16_t)(next_rand() % 101u);
apply_row(i, pct);
}
printf("[progress.settings] Randomize\n");
}
static void add_button(ugui_widget_t* w, ugui_button_ext_t* ext, ugui_text_cfg_t* text,
uint8_t id, int16_t x, int16_t y, int16_t bw, int16_t bh,
const char* str, ugui_event_cb_t cb)
{
ugui_widget_button_init(&s_root, w, ext);
ugui_widget_set_area(w, x, y, bw, bh);
ugui_widget_set_id(w, id);
ugui_widget_button_set_style(w, true, 5u, 1u, UGUI_THEME_SURFACE, UGUI_THEME_ACCENT);
#ifdef UGUI_ENABLE_FONT
ugui_text_cfg_init(text, str, &lexend_14pt_2bpp, UGUI_THEME_TEXT,
UGUI_ALIGN_CENTER, (ugui_point_t){ 0, 0 }, 1u);
ugui_widget_button_set_text(w, text);
#endif
ugui_widget_set_event_cb(w, cb,
UGUI_EMASK_CLICK | UGUI_EMASK_DOWN | UGUI_EMASK_UP
| UGUI_EMASK_KEY_CONFIRM);
ugui_screen_add_widget(&s_screen, w);
#if UGUI_ENABLE_KEYPAD
ugui_screen_add_focus(&s_screen, w);
#endif
}
static void add_label(ugui_widget_t* w, ugui_label_ext_t* ext, uint8_t id,
int16_t x, int16_t y, int16_t cw, int16_t ch,
const char* str, ugui_align_t align)
{
ugui_widget_label_init(&s_root, w, ext);
ugui_widget_set_area(w, x, y, cw, ch);
ugui_widget_set_id (w, id);
ugui_widget_label_set_style(w, /*bg_fill=*/false, UGUI_THEME_SURFACE, str,
&lexend_14pt_2bpp, UGUI_THEME_TEXT, align, 1u);
ugui_screen_add_widget(&s_screen, w);
}
/* --- build it (in your screen's init) --- */
uint8_t i;
for (i = 0u; i < ROW_N; i++) {
int16_t row_y = (int16_t)(PANEL_Y + (int16_t)i * ROW_STEP
+ (ROW_STEP - BAR_H) / 2);
add_label(&s_label[i], &s_label_ext[i], (uint8_t)(WDGT_ID_SLOT4 + i),
LBL_X, row_y, LBL_W, BAR_H, k_row_label[i],
(ugui_align_t)(UGUI_ALIGN_LEFT | UGUI_ALIGN_V_CENTER));
ugui_widget_progress_init(&s_root, &s_bar_w[i], &s_bar_ext[i]);
ugui_widget_set_area(&s_bar_w[i], BAR_X, row_y, BAR_W, BAR_H);
ugui_widget_set_id(&s_bar_w[i], (uint8_t)(WDGT_ID_SLOT0 + i));
#ifdef UGUI_ENABLE_FONT
ugui_text_cfg_init(&s_bar_text[i], "", &lexend_14pt_2bpp, UGUI_THEME_KNOB,
UGUI_ALIGN_CENTER, (ugui_point_t){ 0, 0 }, 1u);
ugui_widget_progress_set_text(&s_bar_w[i], &s_bar_text[i]);
#endif
apply_row(i, k_row_init[i]);
ugui_screen_add_widget(&s_screen, &s_bar_w[i]);
}
add_button(&s_randomize_btn, &s_randomize_ext, &s_randomize_text, WDGT_ID_RANDOMIZE,
PANEL_X, BTN_Y, PANEL_W, BTN_H, "Randomize", on_randomize);
From this widget to a working app
Everything above is the widget-specific code. The scaffolding it drops into — storage, HAL, main loop, display-mode bring-up — is the same for every app: copy it from the Application Skeleton.