cryptnox-pos 1.0.0
Standalone USDC payment terminal firmware (ESP32 + Cryptnox smart card)
Loading...
Searching...
No Matches
ui_internal.h
Go to the documentation of this file.
1/*
2 * SPDX-License-Identifier: LGPL-3.0-or-later
3 * Copyright (c) 2026 Cryptnox SA
4 */
5
11
12#ifndef UI_INTERNAL_H
13#define UI_INTERNAL_H
14
15#include "ui.h"
16
17#include <Arduino.h>
18
19#include <SPI.h>
20
21#include <TFT_eSPI.h>
22
23#include <XPT2046_Touchscreen.h>
24
25#include <stdio.h>
26
27#include <string.h>
28
29#include <inttypes.h>
30
31#include <time.h> /* the status-band clock */
32
33#include "lvgl.h"
34
35#include "logo_img.h"
36
37#include "logo_small.h"
38
39#include "logo_mid.h" /* 80px, the welcome card — tools/gen_logo_mid.py */
40
41#include "chain_icons.h"
42
43#include "tap_icon.h" /* the "tap your card" mark — tools/gen_tap_icon.py */
44
45#include "assets.h" /* the per-asset table: ticker, standard, caption, network */
46
47#include "settings.h"
48
49#include "money.h" /* keypad cents, the native cap, amount text — host-tested */
50
51#include "touch_cal.h" /* two-point calibration arithmetic, host-tested */
52
53#include "civil_time.h" /* civil_local_offset_min() — the clock's DST, host-tested */
54
55#include "provision.h" /* QR payload + the pending payout-address handshake */
56
57#include "ota.h" /* running version + the update window and its handshake */
58
59#include "ota_version.h" /* ota_version_display() — the 'v' is added for the screen */
60
61#include "freertos/FreeRTOS.h"
62
63#include "freertos/task.h"
64
65#include "freertos/semphr.h" /* s_ui_mx */
66
67#include "esp_timer.h"
68
69#include "wdt.h" /* the UI loop is on the task watchdog */
70
71#include "esp_log.h"
72
73#include "esp_system.h" /* esp_restart() for factory reset */
74
75#include "driver/ledc.h"
76
77#include "CW_Utils.h" /* hardened memory primitives (CODING_RULES §1.4) */
78
79/* Plus Jakarta Sans for titles, buttons and figures, Inter for small text;
80 * one weight per role — main/fonts/, tools/gen_fonts.py.
81 * Spelled out rather than LV_FONT_DECLARE, which cppcheck cannot expand
82 * without the LVGL headers (unknownMacro fails CI). */
83extern const lv_font_t font_inter_14; /* Inter Regular: body, captions */
84
85extern const lv_font_t font_inter_14_medium; /* Inter Medium: values, clock */
86
87extern const lv_font_t font_pjs_20_medium; /* Medium: titles and messages */
88
89extern const lv_font_t font_pjs_20_semibold; /* SemiBold: button labels */
90
91extern const lv_font_t font_pjs_28_semibold; /* SemiBold: amounts */
92
93extern const lv_font_t font_pjs_28_light; /* Light: keypad digits */
94
95extern const lv_font_t font_icons_48; /* LV_SYMBOL_OK/CLOSE/WARNING */
96
97/******************************************************************
98 * 2. Hardware — panel (TFT_eSPI) and touch (XPT2046, separate SPI bus)
99 ******************************************************************/
100#define T_CS 33
101
102#define T_IRQ 36
103
104#define T_CLK 25
105
106#define T_MOSI 32
107
108#define T_MISO 39
109
110/* Portrait orientation (240x320) — natural for a hand-held POS terminal. */
111#define SCR_W 240
112
113#define SCR_H 320
114
115/* Splash logo X trim, tuned by eye on the panel: the bitmap is geometrically
116 * centred, but 0 reads as too far right. A calibration value — do not "correct"
117 * it from the image geometry. */
118#define LOGO_X_NUDGE (-4)
119
120/******************************************************************
121 * 3. Theme — light, minimal: white bg, black ink
122 ******************************************************************/
123#define COL_BG lv_color_hex(0xFFFFFF) /* white — page background */
124
125#define COL_SURFACE lv_color_hex(0xF2F2F2) /* light grey — cards/secondary */
126
127#define COL_TEXT lv_color_hex(0x000000) /* black — primary text */
128
129#define COL_DIM lv_color_hex(0x9A9A9A) /* grey — secondary labels */
130
131#define COL_TITLE lv_color_hex(0x424242) /* dark grey — screen titles */
132
133/* Slate, not black: the setup portal's hue, so panel and browser match. Tuned
134 * on the panel: this is the portal's DARK-scheme accent (--accf, 13.5:1); its
135 * light ink #2C3E50 (11:1) reads washed out on this TFT. Text on it is COL_BG. */
136#define COL_ACCENT lv_color_hex(0x22303D) /* slate — chrome, tabs, controls */
137
138/* The sale's two buttons: the one that commits is filled (WHITE label, 16.4:1),
139 * the one that backs out is an outline button in the card's white. Its fill is
140 * the card's, so the hairline in make_ghost_button() is load-bearing: keep it. */
141#define COL_ACTION lv_color_hex(0x101F2E) /* charcoal blue — Charge, Confirm */
142
143/* The page behind the white card: a vertical ramp, pale sky deepening into
144 * COL_PAGE_GRAD. The ramp is what separates the card (the top is barely off
145 * white), so do not flatten it; the COL_DIM home indicator must stay far darker. */
146#define COL_PAGE lv_color_hex(0xE2F5FF) /* pale sky — head of the ramp */
147
148#define COL_PAGE_GRAD lv_color_hex(0xA8D8F0) /* deeper sky — foot of it */
149
150/* The admin side has no page colour of its own: it is plain COL_BG. */
151#define COL_HOME_BAR COL_DIM /* grey — the swipe handle */
152
153#define COL_WARN lv_color_hex(0xE39A2D) /* amber — "not confirmed yet" */
154
155#define COL_SUCCESS lv_color_hex(0x1E9E50) /* green — "Sent" */
156
157#define COL_DANGER lv_color_hex(0xD63A3A) /* red — failures / reset */
158
159#define COL_BORDER lv_color_hex(0xE0E0E0) /* light grey — hairlines */
160
161/* Corner radius for every button on the panel, and the tab bar's segments, so
162 * the two shapes match — see make_button. */
163#define BTN_RADIUS 6
164
165/******************************************************************
166 * 3b. Layout metrics — shared so every screen's header lines up
167 ******************************************************************/
168#define HDR_TITLE_Y 11 /* title offset — optically centred in the
170 42px band above the divider (font_pjs_20_medium) */
171#define HDR_DIVIDER_Y 42 /* rule under the title */
172
173#define ACT_BTN_H 46 /* bottom action-button height */
174
175#define ACT_BTN_Y (-8) /* bottom action-button offset */
176
177/* Every text field's vertical inset (height = one line + twice this). Not in
178 * the theme's s_st_field: that style is on the Wi-Fi keyboard too, and the
179 * theme sets no geometry. */
180#define FIELD_PAD_V 8
181
182#define MENU_BTN_W 42
183
184#define MENU_BTN_H 30
185
186#define MENU_BTN_X 4
187
188#define MENU_BTN_Y 6
189
190/* Asset selector — on the amount's own row, hard right, so it reads as the
191 * figure's currency. It carries the ticker; the figure is a bare number.
192 *
193 * No fixed width: the pill is content-sized flex (tickers vary) and
194 * amount_row_place() measures it. 42 tall is 3px of air above and below the
195 * 36px badge (BADGE_SZ, with the icon helpers). */
196#define ASSET_BTN_H 42
198/* Both in CARD coordinates — the amount screen builds into the white card. */
199#define ASSET_BTN_X (-8) /* right edge inset */
200
201#define ASSET_BTN_Y 10 /* the figure's row is centred on THIS */
202
203/* The figure's row shares the selector's line, clear of the keypad at 90; its
204 * offsets depend on what has been typed — see amount_row_place(). */
205#define ASSET_BTN_PAD 8 /* badge inset from the left edge */
206
207#define TAB_PAD 12 /* settings tab page padding */
208
209#define TAB_W (SCR_W - (2 * TAB_PAD)) /* usable tab width */
210
211/******************************************************************
212 * 4. LVGL display + input plumbing
213 ******************************************************************/
214#define LV_TICK_PERIOD_MS 2
215
216/* Touch calibration. Two targets: two points are the whole of the linear map
217 * touch_to_screen() applies.
218 * ponytail: two-point linear. If a panel turns out skewed rather than offset
219 * and scaled, the upgrade is an affine map and four corners.
220 *
221 * Steps 0 and 1 capture a corner each; step 2 applies the result live and asks
222 * the operator to confirm by tapping with it, so a calibration that makes Save
223 * unreachable is never stored, and the deadline restores the old numbers. */
224#define CAL_INSET 20 /* target centre, in from each corner */
225
226#define CAL_VERIFY_MS 20000U /* un-confirmed calibration reverts after this */
228/* Wi-Fi picker */
229#define WIFI_MAX_APS 16
230
231/* Admin code (admin panel lock; it opens the payout addresses). Six digits for
232 * a new code: under the escalating penalty (capped at an hour) that is a few
233 * dozen guesses a night against 10^6. The merchant may choose up to
234 * ADMIN_CODE_MAX.
235 *
236 * The unlock screen also accepts four-digit codes stored by older builds — they
237 * must keep opening the menu (it gates the factory reset too) — so only the
238 * creation screen enforces the six-digit floor. */
239#define ADMIN_CODE_MIN 6
240
241#define ADMIN_CODE_MIN_STORED 4 /* shortest code an older build could store */
242
243#define ADMIN_CODE_MAX 9
244
245/******************************************************************
246 * 6. Button actions
247 ******************************************************************/
253 /* Config portal: accept/reject a proposed value, finish the wizard. */
256 /* Asset selector (amount screen and the Tx tab): network, then the coin. */
258 /* The admin web page: open it (QR to scan), close it, resolve an upload. */
260 /* Touch calibration: start it, keep the result, put the old one back. */
262 /* One action per chain, contiguous, so an action's offset from here IS its
263 * pos_chain_t (ACT_CHAIN_OF below, decoded in btn_event_cb). KEEP LAST: the
264 * block runs to POS_CHAIN__COUNT and nothing may share its numbers. */
266};
269#define ACT_CHAIN_OF(chain) \
270 static_cast<BtnAction>(ACT_CHAIN_BASE + static_cast<int>(chain))
271
272#define SETTINGS_TAB_COUNT 4
273
274#define TAB_ABOUT 3
275
276/* From 100.00 up, the cents move to the small font so the figure fits beside
277 * the asset button on the row. Below 100 there is room for all of it. */
278#define AMOUNT_SMALL_CENTS_FROM 10000ULL /* 100.00 in cents */
280/* Air between the figure and the selector, so they read as two things. */
281#define AMOUNT_ROW_GAP 8
283/* Left gutter the figure may never cross — see amount_row_place(). */
284#define AMOUNT_ROW_MIN_X 4
285
286/******************************************************************
287 * 6b. Sale-flow page chrome
288 *
289 * Sky page, white rounded card, and the home indicator (the admin panel's
290 * handle). build_page() screens place children into the CARD, so (0,0) is the
291 * card's top-left. Only the sale uses this; the admin panel stays plain white.
292 ******************************************************************/
293#define CARD_X 8
294
295#define CARD_Y 28
296
297#define CARD_W (SCR_W - (2 * CARD_X)) /* 224 */
298
299#define CARD_H 262 /* 28..290; home bar sits below */
300
301#define CARD_PAD 10
303/* Bottom action button, in card coordinates. */
304#define CARD_BTN_H 44
305
306#define CARD_BTN_Y (-10)
307
308#define CARD_BTN_W (CARD_W - (2 * CARD_PAD))
309
310/* The status band, left to right: clock, the TEST chip when there is one, the
311 * Wi-Fi mark. Fixed zones, not measured, so nothing moves as the minute ticks.
312 *
313 * Everything sits on one optical centre line at y≈12.5: font_inter_14_medium
314 * draws an 18px box with its 11px cap 4 down (so text at 3 puts the cap at
315 * 7..18), the Wi-Fi mark is 13 tall at 6. Move one and move the other.
316 *
317 * CLOCK_W and CHIP_W are reserves rather than the real widths — "00:00", the
318 * widest time, measures ~40 against 42, "TEST" with its pads ~48 against 56. */
319#define BAND_Y 3 /* text top: clock and chip */
320
321#define CLOCK_X 10
322
323#define CLOCK_Y BAND_Y
324
325#define CLOCK_W 42
326
327#define CHIP_X (CLOCK_X + CLOCK_W + 6)
328
329#define CHIP_Y 3 /* 20px tall, so 3 centres it on the band */
330
331/* Steps of one sale, passed to build_page(). Nothing draws them. */
332enum {
339};
340
341/* Round icon disc with a glyph — the coin mark in a pill's left slot, and (at
342 * CHIP_SZ) the network chip clipped to its corner. Never clickable: it sits
343 * inside a pill button, and a clickable child would swallow that tap. */
344#define COIN_SZ 30
345
346#define TAP_MARK_H 65
347
348/* Selector row in the style of button_style.png: full-radius grey pill, round
349 * icon on the left, title over a dim subtitle, chevron on the right. The icon
350 * is left to the caller (asset badge or glyph disc):
351 *
352 * lv_obj_t *p = make_pill(...);
353 * lv_obj_align(make_asset_badge(p, chain), LV_ALIGN_LEFT_MID, PILL_ICON_X, 0);
355 * @p w is in pixels on purpose — lv_pct() cannot be measured for the subtitle. */
356#define PILL_H 52
357
358#define PILL_ICON_X 10
359
360/* Card geometry for the two update modals. 228 wide leaves 212 inside the 8 px
361 * pad; wrapped text gets 200 so it clears the rounded corners. The text is
362 * runtime-length, so blocks stack with lv_obj_align_to() and ota_fit_card()
363 * grows the card to fit. */
364#define OTA_CARD_W 228
365
366#define OTA_TEXT_W 200
367
368/* Masked one-line code field, with no soft-keyboard popup — the on-screen keypad
369 * is the only input. Shared by the card PIN and the admin code, both paired
370 * with the reveal eye (a blind mistype on a resistive panel is otherwise opaque).
371 *
372 * The code screens place field and eye on the keypad's columns — see
373 * make_code_row(); the Wi-Fi passphrase uses CODE_FIELD_W/CODE_FIELD_X. */
374#define CODE_EYE_GAP 6
375
376#define CODE_FIELD_W(kbd_w) ((kbd_w) - MENU_BTN_W - CODE_EYE_GAP)
377
378#define CODE_FIELD_X (-(MENU_BTN_W + CODE_EYE_GAP) / 2)
379
380/* Numeric keypad: no key boxes — black glyphs on white, grey flash on press.
381 * The map is static because lv_btnmatrix keeps the pointer.
382 *
383 * ONE WIDTH for both code screens (card PIN and admin code), taken from the
384 * sale card, so the two look identical. */
385#define CODE_KBD_W (CARD_W - (2 * CARD_PAD))
386
387/* ── Shared between the ui*.cpp files ─────────────────────────── */
388
389extern const char *TAG;
390extern TFT_eSPI tft;
391extern SPIClass touchSPI;
392extern XPT2046_Touchscreen touch;
393void theme_init(void);
394extern lv_color_t s_buf[SCR_W * 40];
395extern lv_disp_draw_buf_t s_draw_buf;
396extern lv_disp_drv_t s_disp_drv;
397extern lv_indev_drv_t s_indev_drv;
398void disp_flush(lv_disp_drv_t *drv, const lv_area_t *area, lv_color_t *px);
399extern uint16_t s_cal_xmin;
400extern uint16_t s_cal_xmax;
401extern uint16_t s_cal_ymin;
402extern uint16_t s_cal_ymax;
403void touch_cal_load(void);
404bool touch_raw(int16_t *rx, int16_t *ry);
405extern uint32_t s_input_block_until;
406extern bool s_wait_release;
407extern lv_obj_t *s_page_card;
408extern volatile bool s_swipe_admin;
409void indev_read(lv_indev_drv_t *drv, lv_indev_data_t *data);
410void tick_cb(void *arg);
411extern uint8_t s_brightness;
412void backlight_set_pct(uint8_t pct);
413void backlight_init(uint8_t pct);
414extern ui_event_cb_t s_cb;
415extern volatile ui_screen_t s_req_screen;
416extern uint64_t s_amount_units;
417extern uint64_t s_confirm_amount;
418extern char s_confirm_addr[64];
419extern char s_confirm_fee[40];
421extern char s_tx_info[72];
422extern lv_obj_t *s_tx_info_lbl;
423extern uint8_t s_cal_step;
424extern int16_t s_cal_raw[2][2];
425extern bool s_cal_pressed;
426extern int16_t s_cal_last_x;
427extern int16_t s_cal_last_y;
428extern uint32_t s_cal_deadline;
429extern lv_obj_t *s_cal_countdown;
430extern lv_obj_t *s_sheet;
431extern volatile bool s_sheet_pending;
432extern char s_card_note[64];
433extern lv_obj_t *s_amount_label;
434extern lv_obj_t *s_amount_cents_label;
435extern lv_obj_t *s_amount_row;
436extern uint64_t s_amount_cents;
437extern lv_obj_t *s_asset_btn;
438extern lv_obj_t *s_asset_arrow;
439extern lv_obj_t *s_charge_btn;
440extern lv_obj_t *s_clock_lbl;
441extern bool s_charge_busy;
442extern lv_obj_t *s_pin_ta;
443extern char s_pin[16];
444extern uint8_t s_pin_len;
446extern uint16_t s_ap_count;
447extern char s_wifi_ssid[33];
448extern char s_wifi_pass[65];
449extern char s_wifi_note[64];
450extern lv_obj_t *s_wifi_pass_ta;
451extern lv_obj_t *s_wifi_eye_lbl;
452extern lv_obj_t *s_pin_eye_lbl;
453extern lv_obj_t *s_admin_eye_lbl;
454extern char s_wifi_caption[24];
455extern char s_wifi_name[33];
456extern char s_boot_step[40];
457extern lv_obj_t *s_boot_step_lbl;
458extern lv_obj_t *s_fee_max_lbl;
459extern lv_obj_t *s_fee_prio_lbl;
460extern volatile int s_prov_step;
461extern char s_prov_msg[64];
463extern char s_boot_detail[64];
464extern lv_obj_t *s_admin_ta;
465extern lv_obj_t *s_admin_note_lbl;
466extern char s_admin_first[ADMIN_CODE_MAX + 1];
467extern char s_admin_note[48];
468extern bool s_admin_confirming;
469extern char s_welcome_sub[96];
470extern uint32_t s_admin_lock_start;
471extern uint32_t s_admin_lock_ms;
472extern bool s_admin_for_portal;
473extern bool s_pin_for_card;
474extern const char *s_addr_usdc;
475extern const char *s_addr_dest;
476extern lv_obj_t *s_reset_btn;
477extern lv_obj_t *s_close_btn;
478extern uint16_t s_settings_tab;
481const char *asset_name(pos_chain_t c = settings_get_chain());
485void set_wifi_progress(const char *caption, const char *name);
486uint64_t amount_cents_max(void);
487void charge_set_busy(void);
488void code_field_reveal(lv_obj_t *ta, lv_obj_t *eye_lbl);
489void btn_event_cb(lv_event_t *e);
490lv_obj_t *make_button(lv_obj_t *parent, const char *label, lv_color_t bg,
491 lv_color_t fg, lv_coord_t w, lv_coord_t h,
492 lv_align_t align, lv_coord_t x, lv_coord_t y,
493 BtnAction act, const lv_font_t *font);
494lv_obj_t *make_label(lv_obj_t *parent, const char *txt, lv_color_t color,
495 const lv_font_t *font, lv_align_t align,
496 lv_coord_t x, lv_coord_t y);
497lv_obj_t *make_ghost_button(lv_obj_t *parent, const char *label,
498 lv_coord_t w, lv_align_t align,
499 lv_coord_t x, lv_coord_t y, BtnAction act);
500void make_divider(lv_obj_t *parent, lv_coord_t y);
501lv_obj_t *make_glyph_disc(lv_obj_t *parent, const char *sym,
502 lv_color_t bg, lv_coord_t sz);
503lv_obj_t *make_asset_badge(lv_obj_t *parent, pos_chain_t chain);
504lv_obj_t *make_asset_button(lv_obj_t *parent);
505void asset_btn_set_compact(bool compact);
506lv_obj_t *make_net_badge(lv_obj_t *parent, pos_net_t net);
507void make_tap_mark(lv_obj_t *parent, lv_coord_t y);
508lv_obj_t *make_pill(lv_obj_t *parent, const char *title, const char *sub,
509 lv_coord_t w, lv_coord_t y, BtnAction act,
510 bool leaf = false);
511lv_obj_t *make_field(lv_obj_t *parent, const char *caption,
512 const char *value, lv_color_t col = COL_TEXT);
513void clear_screen(void);
514extern volatile bool s_tz_dirty;
515void paint_page(lv_obj_t *obj);
516lv_obj_t *make_card(lv_obj_t *parent);
517lv_obj_t *build_page(int step, bool band = true);
518void settings_persist(void);
519void build_settings(void);
520void build_touch_cal(void);
521void touch_cal_poll(void);
522extern bool s_portal_modal;
523void close_modal(void);
524lv_obj_t *open_modal(lv_coord_t w, lv_coord_t h);
525void open_reset_confirm(void);
526lv_obj_t *ota_text(lv_obj_t *card, lv_obj_t *above, const char *txt,
527 lv_color_t col, const lv_font_t *font);
528void ota_fit_card(lv_obj_t *card, lv_obj_t *last, lv_coord_t buttons_h);
529void open_portal_window(void); /* the config page: QR code + passphrase card */
530void open_ota_gone(void);
531void build_ota_confirm(void);
532void open_network_picker(void);
534lv_obj_t *make_icon_button(const char *sym, BtnAction act,
535 lv_obj_t *parent = NULL);
536void add_test_chip(void);
537lv_obj_t *make_title(const char *txt, bool has_icon,
538 lv_obj_t *parent = NULL);
539void build_header(const char *title);
540void build_welcome(void);
541void build_prov(void);
542void build_prov_confirm(void);
543void build_card_wait(void);
544void build_splash(void);
545void build_amount(void);
546void build_confirm(void);
547lv_obj_t *make_numeric_keypad(lv_event_cb_t cb, lv_obj_t *parent = NULL,
548 lv_coord_t w = CODE_KBD_W,
549 lv_coord_t h = 210);
550lv_obj_t *make_code_row(lv_obj_t *host, lv_obj_t *kb, uint32_t max_len,
551 const char *hint, BtnAction eye_act,
552 lv_obj_t **eye_lbl);
553void build_pin(void);
554uint32_t admin_penalty_ms(uint8_t fails);
555void build_admin_set(void);
556void build_admin_unlock(void);
557void build_wifi_list(void);
558void build_wifi_pass(void);
559void build_wifi_connecting(void);
560void pop_in(lv_obj_t *obj);
561void build_tx_status(void);
562void build_boot_error(void);
563void signal_init(void);
564void render_requested_screen(void);
565
566#endif /* UI_INTERNAL_H */
What each selectable asset IS — one row per pos_chain_t.
pos_net_t
A network, as the picker's first step offers it.
Definition assets.h:51
TZ-independent calendar arithmetic and date-string parsing.
static const char *const TAG
Definition eth_rpc.cpp:33
lv_font_t font_icons_48
lv_font_t font_inter_14
lv_font_t font_inter_14_medium
lv_font_t font_pjs_20_medium
lv_font_t font_pjs_20_semibold
lv_font_t font_pjs_28_light
lv_font_t font_pjs_28_semibold
The sale's arithmetic: keypad cents, base units, wei, fees, calldata.
Firmware slot handling: receive an image into the idle slot, verify it, and install it only once some...
Dotted version comparison, for deciding whether an update goes forwards or backwards.
static net_wifi_ap_t s_aps[PROV_MAX_APS]
static uint16_t s_ap_count
static ui_event_cb_t s_cb
The config portal: one web app for setting a terminal up and for administering it afterwards,...
pos_chain_t settings_get_chain(void)
Selected chain, or POS_CHAIN_ETH_USDC if never set.
Definition settings.cpp:165
Persistent device settings stored in NVS (backlight, Wi-Fi creds).
pos_chain_t
Which chain (and therefore which asset) the terminal charges in.
Definition settings.h:33
A scanned access point (subset of fields the UI needs).
Definition net.h:33
One selectable asset.
Definition assets.h:66
Touch arithmetic: two-point calibration, and the second-contact guard.
uint64_t s_amount_cents
Definition ui.cpp:77
char s_wifi_name[33]
Definition ui.cpp:115
lv_obj_t * s_sheet
Definition ui.cpp:62
char s_wifi_note[64]
Definition ui.cpp:105
bool s_admin_confirming
Definition ui.cpp:149
char s_confirm_fee[40]
Definition ui.cpp:42
lv_obj_t * s_clock_lbl
Definition ui.cpp:90
bool s_charge_busy
Definition ui.cpp:94
uint32_t s_admin_lock_start
Definition ui.cpp:155
char s_admin_note[48]
Definition ui.cpp:148
lv_obj_t * s_fee_max_lbl
Definition ui.cpp:126
int16_t s_cal_last_x
Definition ui.cpp:53
char s_admin_first[ADMIN_CODE_MAX+1]
Definition ui.cpp:147
bool s_cal_pressed
Definition ui.cpp:52
lv_obj_t * s_asset_arrow
Definition ui.cpp:82
char s_wifi_pass[65]
Definition ui.cpp:104
lv_obj_t * s_pin_ta
Definition ui.cpp:98
lv_obj_t * s_amount_row
Definition ui.cpp:76
char s_prov_msg[64]
Definition ui.cpp:136
const char * s_addr_dest
Definition ui.cpp:168
volatile bool s_sheet_pending
Definition ui.cpp:63
lv_obj_t * s_cal_countdown
Definition ui.cpp:57
pos_chain_t s_view_chain
Definition ui.cpp:186
ui_tx_state_t s_tx_state
Definition ui.cpp:46
lv_obj_t * s_charge_btn
Definition ui.cpp:86
lv_obj_t * s_amount_cents_label
Definition ui.cpp:73
ui_boot_err_t s_boot_err
Definition ui.cpp:143
char s_boot_step[40]
Definition ui.cpp:119
lv_obj_t * s_fee_prio_lbl
Definition ui.cpp:127
lv_obj_t * s_tx_info_lbl
Definition ui.cpp:48
char s_pin[16]
Definition ui.cpp:99
lv_obj_t * s_pin_eye_lbl
Definition ui.cpp:108
char s_wifi_ssid[33]
Definition ui.cpp:103
char s_confirm_addr[64]
Definition ui.cpp:41
uint64_t s_amount_units
Definition ui.cpp:37
uint8_t s_pin_len
Definition ui.cpp:100
lv_obj_t * s_amount_label
Definition ui.cpp:72
lv_obj_t * s_wifi_eye_lbl
Definition ui.cpp:107
uint8_t s_cal_step
Definition ui.cpp:50
lv_obj_t * s_reset_btn
Definition ui.cpp:171
bool s_pin_for_card
Definition ui.cpp:164
char s_tx_info[72]
Definition ui.cpp:47
lv_obj_t * s_boot_step_lbl
Definition ui.cpp:120
int16_t s_cal_raw[2][2]
Definition ui.cpp:51
int16_t s_cal_last_y
Definition ui.cpp:54
lv_obj_t * s_admin_ta
Definition ui.cpp:145
volatile ui_screen_t s_req_screen
Definition ui.cpp:34
uint64_t s_confirm_amount
Definition ui.cpp:40
uint16_t s_settings_tab
Definition ui.cpp:180
lv_obj_t * s_admin_eye_lbl
Definition ui.cpp:109
volatile int s_prov_step
Definition ui.cpp:132
uint32_t s_admin_lock_ms
Definition ui.cpp:156
lv_obj_t * s_close_btn
Definition ui.cpp:172
lv_obj_t * s_asset_btn
Definition ui.cpp:81
char s_welcome_sub[96]
Definition ui.cpp:151
lv_obj_t * s_admin_note_lbl
Definition ui.cpp:146
char s_wifi_caption[24]
Definition ui.cpp:114
char s_card_note[64]
Definition ui.cpp:67
bool s_admin_for_portal
Definition ui.cpp:159
const char * s_addr_usdc
Definition ui.cpp:167
uint32_t s_cal_deadline
Definition ui.cpp:56
char s_boot_detail[64]
Definition ui.cpp:144
lv_obj_t * s_wifi_pass_ta
Definition ui.cpp:106
Touchscreen UI API: screens, events and transaction states for the CYD (ILI9341 + XPT2046) payment fl...
ui_screen_t
Top-level screens of the payment flow.
Definition ui.h:35
ui_tx_state_t
States shown on the transaction-status screen.
Definition ui.h:94
ui_boot_err_t
Startup faults shown on UI_SCREEN_BOOT_ERROR.
Definition ui.h:113
void(* ui_event_cb_t)(ui_event_t event, uint64_t payload)
Callback invoked from the UI task on user interaction.
Definition ui.h:128
bool s_portal_modal
Definition ui_admin.cpp:423
volatile bool s_swipe_admin
Definition ui_hal.cpp:103
lv_indev_drv_t s_indev_drv
Definition ui_hal.cpp:21
lv_obj_t * s_page_card
Definition ui_hal.cpp:84
bool s_wait_release
Definition ui_hal.cpp:80
uint16_t s_cal_ymax
Definition ui_hal.cpp:42
lv_disp_draw_buf_t s_draw_buf
Definition ui_hal.cpp:19
uint8_t s_brightness
Definition ui_hal.cpp:179
TFT_eSPI tft
Definition ui_hal.cpp:14
lv_disp_drv_t s_disp_drv
Definition ui_hal.cpp:20
uint32_t s_input_block_until
Definition ui_hal.cpp:79
uint16_t s_cal_xmin
Definition ui_hal.cpp:39
uint16_t s_cal_ymin
Definition ui_hal.cpp:41
lv_color_t s_buf[SCR_W *40]
Definition ui_hal.cpp:18
uint16_t s_cal_xmax
Definition ui_hal.cpp:40
const char * asset_network(pos_chain_t c=settings_get_chain())
Definition ui.cpp:204
void build_admin_set(void)
Definition ui_admin.cpp:922
void open_network_picker(void)
Definition ui_admin.cpp:656
lv_obj_t * make_glyph_disc(lv_obj_t *parent, const char *sym, lv_color_t bg, lv_coord_t sz)
@ PAY_STEP_NONE
@ PAY_STEP_AUTH
@ PAY_STEP_AMOUNT
@ PAY_STEP_TAP
@ PAY_STEP__COUNT
@ PAY_STEP_REVIEW
lv_obj_t * build_page(int step, bool band=true)
void build_wifi_list(void)
Definition ui_setup.cpp:314
void build_admin_unlock(void)
Definition ui_admin.cpp:929
void build_pin(void)
Definition ui_sale.cpp:643
void set_wifi_progress(const char *caption, const char *name)
Definition ui.cpp:247
bool touch_raw(int16_t *rx, int16_t *ry)
Definition ui_hal.cpp:49
lv_obj_t * make_asset_badge(lv_obj_t *parent, pos_chain_t chain)
uint32_t admin_penalty_ms(uint8_t fails)
Definition ui_admin.cpp:739
void pop_in(lv_obj_t *obj)
Definition ui_sale.cpp:673
void settings_persist(void)
Definition ui_admin.cpp:19
const char * asset_caption(pos_chain_t c=settings_get_chain())
Definition ui.cpp:210
void tick_cb(void *arg)
Definition ui_hal.cpp:165
#define CODE_KBD_W
lv_obj_t * make_button(lv_obj_t *parent, const char *label, lv_color_t bg, lv_color_t fg, lv_coord_t w, lv_coord_t h, lv_align_t align, lv_coord_t x, lv_coord_t y, BtnAction act, const lv_font_t *font)
XPT2046_Touchscreen touch
lv_obj_t * make_code_row(lv_obj_t *host, lv_obj_t *kb, uint32_t max_len, const char *hint, BtnAction eye_act, lv_obj_t **eye_lbl)
Definition ui_sale.cpp:615
void asset_btn_set_compact(bool compact)
lv_obj_t * make_icon_button(const char *sym, BtnAction act, lv_obj_t *parent=NULL)
void build_prov(void)
Definition ui_setup.cpp:65
void touch_cal_poll(void)
Definition ui_admin.cpp:397
void btn_event_cb(lv_event_t *e)
Definition ui.cpp:306
void make_divider(lv_obj_t *parent, lv_coord_t y)
lv_obj_t * make_net_badge(lv_obj_t *parent, pos_net_t net)
#define ADMIN_CODE_MAX
lv_obj_t * make_ghost_button(lv_obj_t *parent, const char *label, lv_coord_t w, lv_align_t align, lv_coord_t x, lv_coord_t y, BtnAction act)
void build_splash(void)
Definition ui_sale.cpp:295
void request_screen(ui_screen_t s)
Definition ui.cpp:241
lv_obj_t * make_label(lv_obj_t *parent, const char *txt, lv_color_t color, const lv_font_t *font, lv_align_t align, lv_coord_t x, lv_coord_t y)
void close_modal(void)
Definition ui_admin.cpp:424
void build_wifi_pass(void)
Definition ui_setup.cpp:375
volatile bool s_tz_dirty
void build_card_wait(void)
Definition ui_setup.cpp:271
uint64_t amount_cents_max(void)
Definition ui.cpp:265
void build_settings(void)
Definition ui_admin.cpp:64
void backlight_set_pct(uint8_t pct)
Definition ui_hal.cpp:180
void touch_cal_load(void)
Definition ui_hal.cpp:43
void code_field_reveal(lv_obj_t *ta, lv_obj_t *eye_lbl)
Definition ui_sale.cpp:286
void make_tap_mark(lv_obj_t *parent, lv_coord_t y)
void open_coin_picker(pos_net_t net)
Definition ui_admin.cpp:692
lv_obj_t * make_card(lv_obj_t *parent)
#define SCR_W
const pos_asset_t * asset(pos_chain_t c=settings_get_chain())
Definition ui.cpp:189
void build_tx_status(void)
Definition ui_sale.cpp:734
void build_boot_error(void)
Definition ui_sale.cpp:871
void render_requested_screen(void)
void build_prov_confirm(void)
Definition ui_setup.cpp:225
#define COL_TEXT
lv_obj_t * open_modal(lv_coord_t w, lv_coord_t h)
Definition ui_admin.cpp:434
void indev_read(lv_indev_drv_t *drv, lv_indev_data_t *data)
Definition ui_hal.cpp:104
const char * asset_name(pos_chain_t c=settings_get_chain())
Definition ui.cpp:194
void charge_set_busy(void)
Definition ui_sale.cpp:100
void signal_init(void)
lv_obj_t * make_numeric_keypad(lv_event_cb_t cb, lv_obj_t *parent=NULL, lv_coord_t w=CODE_KBD_W, lv_coord_t h=210)
Definition ui_sale.cpp:576
void paint_page(lv_obj_t *obj)
Lay the sale-flow chrome and return the white card to build into.
void build_header(const char *title)
void build_wifi_connecting(void)
Definition ui_setup.cpp:409
lv_obj_t * make_pill(lv_obj_t *parent, const char *title, const char *sub, lv_coord_t w, lv_coord_t y, BtnAction act, bool leaf=false)
SPIClass touchSPI
void clear_screen(void)
void build_amount(void)
Definition ui_sale.cpp:330
lv_obj_t * ota_text(lv_obj_t *card, lv_obj_t *above, const char *txt, lv_color_t col, const lv_font_t *font)
Definition ui_admin.cpp:477
BtnAction
@ ACT_WIFI_PASS_REVEAL
@ ACT_OTA_NO
@ ACT_CAL_CANCEL
@ ACT_PIN_CANCEL
@ ACT_NET_PICK
@ ACT_ADMIN_REVEAL
@ ACT_MODAL_CLOSE
@ ACT_TX_RECHECK
@ ACT_RESET
@ ACT_SEND
@ ACT_WIFI_CANCEL
@ ACT_NET_POLY
@ ACT_NET_ETH
@ ACT_NEW
@ ACT_CAL_SAVE
@ ACT_PIN_REVEAL
@ ACT_PROV_OK
@ ACT_RESET_CONFIRM
@ ACT_CHAIN_BASE
@ ACT_ADMIN_CANCEL
@ ACT_WELCOME_OK
@ ACT_CANCEL
@ ACT_CONFIRM
@ ACT_PORTAL
@ ACT_WIFI
@ ACT_OTA_OK
@ ACT_TOUCH_CAL
@ ACT_CLOSE
@ ACT_PORTAL_CLOSE
@ ACT_PROV_NO
@ ACT_PROV_FINISH
@ ACT_NET_TRON
void build_welcome(void)
Definition ui_setup.cpp:17
void build_ota_confirm(void)
Definition ui_admin.cpp:593
void ota_fit_card(lv_obj_t *card, lv_obj_t *last, lv_coord_t buttons_h)
Definition ui_admin.cpp:502
lv_obj_t * make_title(const char *txt, bool has_icon, lv_obj_t *parent=NULL)
Screen title, centred but never underneath the top-left icon button.
lv_obj_t * make_field(lv_obj_t *parent, const char *caption, const char *value, lv_color_t col=COL_TEXT)
void build_touch_cal(void)
Definition ui_admin.cpp:331
void theme_init(void)
Install the theme. After lv_disp_drv_register(), before any object.
Definition ui_theme.cpp:157
void disp_flush(lv_disp_drv_t *drv, const lv_area_t *area, lv_color_t *px)
Definition ui_hal.cpp:22
void add_test_chip(void)
lv_obj_t * make_asset_button(lv_obj_t *parent)
void open_reset_confirm(void)
Definition ui_admin.cpp:457
void open_portal_window(void)
Definition ui_admin.cpp:510
void build_confirm(void)
Definition ui_sale.cpp:400
void backlight_init(uint8_t pct)
Definition ui_hal.cpp:186
void open_ota_gone(void)
Definition ui_admin.cpp:581
#define WIFI_MAX_APS
Task-watchdog feed that is safe to call from any task.