From c5f1631b93456e3a084e6b72e55fc442d1e2817c Mon Sep 17 00:00:00 2001 From: Luke Hoersten Date: Tue, 30 Jun 2026 20:50:34 -0500 Subject: firmware: clear panel to Loading screen on new stream connection MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The panel used to hold its last framebuffer during the connect→first-frame gap, flashing a stale old frame before video appeared — more visible now that the Scrypted side no longer sends a bridging snapshot. The wake path already paints the Loading screen, but state_machine_set(AWAKE) is a no-op when the device is already awake (e.g. a stream restart), so the clear didn't happen there. Tie the clear to the stream connection instead: recv-task paints local_screens_show_loading() once per new conn_id, guarded by the decoder lock so the RGB565 present can't race a trailing decode-task paint, and gated on AWAKE so it never draws on a sleeping panel. --- main/stream_server.c | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/main/stream_server.c b/main/stream_server.c index 24646cb..2bc58ac 100644 --- a/main/stream_server.c +++ b/main/stream_server.c @@ -14,6 +14,7 @@ #include "display.h" #include "jpeg_decoder.h" +#include "local_screens.h" #include "state_machine.h" #include "viewport_state.h" @@ -216,6 +217,20 @@ static void handle_client_recv(int fd, const char *peer) conn_id = ++s_conn_id; portEXIT_CRITICAL(&s_slot_mux); + // Clear any stale prior frame to the "Loading..." screen at the start of + // every stream session, so the panel doesn't sit on an old image during + // the connect→first-frame gap (several seconds on a cold prebuffer; the + // Scrypted side no longer sends a bridging snapshot). The wake path also + // shows this, but a stream can start while already AWAKE (e.g. a restart) + // where the state-machine wake is a no-op — this covers that case too. + // Guard with the decoder lock so the RGB565 present can't race a trailing + // decode-task paint from the previous connection; skip if not awake. + if (state_machine_current() == VIEWPORT_STATE_AWAKE && + jpeg_decoder_try_lock(500)) { + local_screens_show_loading(); + jpeg_decoder_unlock(); + } + while (1) { uint8_t first4[4]; if (read_n(fd, first4, 4) != ESP_OK) { -- cgit v1.2.3