Wi-Fi credentials now live in the widget's own NVS (up to 8 networks)
instead of the driver's single slot. The save handler just appends to
the list and reboots, so it no longer calls esp_wifi_set_config in
APSTA mode -- the source of the intermittent could-not-save. A connect
task cycles the saved networks newest-first and holds the first that
connects, re-scanning on drop, so the widget follows you between
locations. The portal lists saved networks with a Forget button and an
add form. An existing driver-stored credential is migrated on first
boot. Verified end to end over the LAN: save persists across reboot,
forget removes.
Cached opentopia stream URLs go stale, and the stored-URL retry path
re-showed the same camera (sometimes a full second time via the history
interaction), which read as frequent repeats. Now opentopia cameras
re-resolve their stream URL on every play and the retry dance is gone; a
last-drawn guard also prevents any camera being drawn twice in a row.
Verified: 29 consecutive cameras, 29 distinct, 0 repeats.
Random mode keeps a ring of the last 1200 cameras (provider|id) and
skips them, giving up after four fully-seen pages. Opentopia pages now
contribute all 19 cameras instead of the first six.
A knob turn still wakes the chip (the RTC can't tell gestures apart), but
the firmware now stays dark and checks the button: held while turning it
boots at once; otherwise the ring glows for 2.5 s waiting for a click and
goes back to deep sleep if none comes. Screen and Wi-Fi never start for
an accidental nudge.
Themes (Phosphor, Pink, Amber, Ice, Terminal) restyle the menu, boot
page and toasts live from the menu; all but Terminal use readable
Montserrat text. Source gains Popular: the top-rated listings walked in
rank order from page 1, alternating providers when mixed.
Power off drops the peripheral rail (PWR_ON low), sleeps the panel and
puts the chip into deep sleep with ext1 wake armed on the encoder pins,
choosing any-low or any-high from the knob's resting state so a single
detent wakes it. The button (GPIO0) is not a wake source on purpose.
Listing pages (rated/newest) and per-camera pages are fetched over HTTPS
with the certificate bundle; the camera page's Live Feed mode yields the
camera's own MJPEG URL (Current Still as fallback), resolved just before
playing and cached in favourites. New Provider menu row: insecam /
opentopia / mixed. cam_info_t gains provider + title fields and the
settings blob a version byte; older favourites and settings still load.
BAT_ADC (GPIO4) sits between two 100k resistors on the switched supply
rail, so it reads the cell on battery and ~4.4 V on USB; above 4.25 V is
reported as USB power. On battery the caption shows a glyph + percentage
from a LiPo OCV table; the menu shows voltage and source. Menu lists now
wrap at both ends.
Hold the knob to open a six-row menu: save/remove the playing camera as
a favourite (12 NVS slots), play or forget favourites, choose the
source (random insecam or favourites), time per camera, listing,
screen and ring brightness, caption, and reboot into Wi-Fi setup.
Settings live in NVS and override the Kconfig first-boot defaults.
Camera URLs are stored with their COUNTER placeholder so favourites get
a fresh cache-buster on every visit.
esp_new_jpeg scales inside the decoder and is 5-6x faster than tjpgd on
the S3 (1280x800 frame: ~100 ms instead of ~600 ms), so MJPEG streams
now play at a few fps. insecam double-encodes some URLs (&); the
entity decoder now loops until stable.
ESP-IDF 5.5 + LVGL 9 firmware that plays random public cameras from
insecam.org on the T-Embed's 320x170 screen, live MJPEG where available,
a new camera every 20 seconds. Knob steps through cameras, LED ring shows
the countdown. Auto-detects the original vs CC1101 board, reuses Wi-Fi
credentials from NVS and falls back to a captive-portal setup hotspot.