fix repeater admin screen timeout buffer t5s3; minor ui fixes web reader screen t5s3

This commit is contained in:
pelgraine
2026-03-13 19:29:54 +11:00
parent 9040873526
commit c60255a44d
5 changed files with 187 additions and 11 deletions

View File

@@ -604,6 +604,49 @@ MyMesh the_mesh(radio_driver, fast_rng, rtc_clock, tables, store
}
}
#ifdef MECK_WEB_READER
// Web reader: context-dependent taps (VKB for text fields, navigation elsewhere)
if (ui_task.isOnWebReader()) {
WebReaderScreen* wr = (WebReaderScreen*)ui_task.getWebReaderScreen();
if (wr) {
if (wr->isReading()) {
// Footer zone tap → open link VKB (if links exist)
if (vy >= 113 && wr->getLinkCount() > 0) {
ui_task.showVirtualKeyboard(VKB_WEB_LINK, "Link #", "", 3);
return 0;
}
return 'd'; // Tap reading area → next page
}
if (wr->isHome()) {
int sel = wr->getHomeSelected();
if (sel == 1) {
// URL bar → open VKB for URL entry
ui_task.showVirtualKeyboard(VKB_WEB_URL, "Enter URL",
wr->getUrlText(), WEB_MAX_URL_LEN - 1);
return 0;
}
if (sel == 2) {
// Search → open VKB for DuckDuckGo search
ui_task.showVirtualKeyboard(VKB_WEB_SEARCH, "Search DuckDuckGo", "", 127);
return 0;
}
return KEY_ENTER; // IRC, bookmarks, history: select
}
if (wr->isWifiSetup()) {
if (wr->isPasswordEntry()) {
// Open VKB for WiFi password entry
ui_task.showVirtualKeyboard(VKB_WEB_WIFI_PASS, "WiFi Password", "", 63);
return 0;
}
return KEY_ENTER; // SSID list: select, failed: retry
}
}
return KEY_ENTER;
}
#endif
// Channel screen: tap footer area → hop path, tap elsewhere → no action
if (ui_task.isOnChannelScreen()) {
ChannelScreen* chScr = (ChannelScreen*)ui_task.getChannelScreen();
@@ -637,6 +680,24 @@ MyMesh the_mesh(radio_driver, fast_rng, rtc_clock, tables, store
}
}
#ifdef MECK_WEB_READER
// Web reader: page turn in reading mode, list scroll elsewhere
if (ui_task.isOnWebReader()) {
WebReaderScreen* wr = (WebReaderScreen*)ui_task.getWebReaderScreen();
if (wr && wr->isReading()) {
if (horizontal) {
return (dx < 0) ? 'd' : 'a'; // swipe left=next page, right=prev
}
return (dy > 0) ? 'd' : 'a'; // swipe down=next, up=prev
}
// HOME / WIFI_SETUP / other: vertical swipe = scroll list
if (!horizontal) {
return (dy > 0) ? 's' : 'w';
}
return 0; // Ignore horizontal swipes on non-reading modes
}
#endif
// Home screen: swipe left = next page, swipe right = previous page
if (ui_task.isOnHomeScreen()) {
if (horizontal) {
@@ -685,6 +746,33 @@ MyMesh the_mesh(radio_driver, fast_rng, rtc_clock, tables, store
return KEY_ENTER; // file list: open
}
#ifdef MECK_WEB_READER
// Web reader: long press for back navigation
if (ui_task.isOnWebReader()) {
WebReaderScreen* wr = (WebReaderScreen*)ui_task.getWebReaderScreen();
if (wr) {
if (wr->isReading()) {
return 'b'; // Back to previous page, or HOME if no history
}
if (wr->isHome()) {
int sel = wr->getHomeSelected();
int bmEnd = 3 + wr->getBookmarkCount();
if (sel >= 3 && sel < bmEnd) {
return '\b'; // Long press on bookmark → delete
}
return 'q'; // All others: exit web reader
}
if (wr->isWifiSetup()) {
return 'q'; // Back from WiFi setup
}
if (wr->isIRCMode()) {
return 'q'; // Back from IRC
}
}
return 'q'; // Default: back out
}
#endif
// Channel screen: long press → compose to current channel
if (ui_task.isOnChannelScreen()) {
uint8_t chIdx = ui_task.getChannelScreenViewIdx();

View File

@@ -1213,9 +1213,10 @@ inline bool RepeaterAdminScreen::doLogin() {
if (the_mesh.uiLoginToRepeater(_contactIdx, _password, timeout_ms)) {
_state = STATE_LOGGING_IN;
_cmdSentAt = millis();
// Add a 1.5s buffer over the mesh estimate; fall back to ADMIN_TIMEOUT_MS
// if the estimate came back zero for any reason.
_loginTimeoutMs = (timeout_ms > 0) ? timeout_ms + 1500 : ADMIN_TIMEOUT_MS;
// Add a 5s buffer over the mesh estimate to account for blocking e-ink
// refreshes (FastEPD ~1-2s per frame, VKB dismiss + login render = 2-3 frames).
// Fall back to ADMIN_TIMEOUT_MS if the estimate came back zero.
_loginTimeoutMs = (timeout_ms > 0) ? timeout_ms + 5000 : ADMIN_TIMEOUT_MS;
_waitingForLogin = true;
return true;
} else {

View File

@@ -4,6 +4,9 @@
#include "NotesScreen.h"
#include "RepeaterAdminScreen.h"
#include "DiscoveryScreen.h"
#ifdef MECK_WEB_READER
#include "WebReaderScreen.h"
#endif
#if HAS_GPS
#include "MapScreen.h"
#endif
@@ -1843,6 +1846,50 @@ void UITask::onVKBSubmit() {
if (_screenBeforeVKB) setCurrScreen(_screenBeforeVKB);
break;
}
#endif
#ifdef MECK_WEB_READER
case VKB_WEB_URL: {
WebReaderScreen* wr = (WebReaderScreen*)getWebReaderScreen();
if (wr && strlen(text) > 0) {
wr->setUrlText(text); // Copy text + set _urlEditing = true
wr->handleInput('\r'); // Triggers auto-prefix + fetch
}
if (_screenBeforeVKB) setCurrScreen(_screenBeforeVKB);
break;
}
case VKB_WEB_SEARCH: {
WebReaderScreen* wr = (WebReaderScreen*)getWebReaderScreen();
if (wr && strlen(text) > 0) {
wr->setSearchText(text); // Copy text + set _searchEditing = true
wr->handleInput('\r'); // Triggers DDG search URL build + fetch
}
if (_screenBeforeVKB) setCurrScreen(_screenBeforeVKB);
break;
}
case VKB_WEB_WIFI_PASS: {
WebReaderScreen* wr = (WebReaderScreen*)getWebReaderScreen();
if (wr && strlen(text) > 0) {
wr->setWifiPassText(text); // Copy password text
wr->handleInput('\r'); // Triggers WiFi connect
}
if (_screenBeforeVKB) setCurrScreen(_screenBeforeVKB);
break;
}
case VKB_WEB_LINK: {
WebReaderScreen* wr = (WebReaderScreen*)getWebReaderScreen();
if (wr && strlen(text) > 0) {
// Activate link input mode, feed digits, then submit
wr->handleInput('l'); // Enter link selection mode
for (int i = 0; text[i]; i++) {
if (text[i] >= '0' && text[i] <= '9') {
wr->handleInput(text[i]);
}
}
wr->handleInput('\r'); // Confirm link number → navigate
}
if (_screenBeforeVKB) setCurrScreen(_screenBeforeVKB);
break;
}
#endif
}
_screenBeforeVKB = nullptr;

View File

@@ -2754,7 +2754,10 @@ private:
display.setCursor(0, footerY);
display.setColor(DisplayDriver::YELLOW);
#if defined(LilyGo_T5S3_EPaper_Pro)
display.print("Swipe:Nav Tap:Select");
if (_wifiState == WIFI_ENTERING_PASS)
display.print("Tap:Type Pass Hold:Bk");
else
display.print("Swipe:Nav Tap:Select");
#else
display.print("Q:Back W/S:Nav Ent:Select");
#endif
@@ -3142,10 +3145,16 @@ private:
char footerBuf[48];
#if defined(LilyGo_T5S3_EPaper_Pro)
bool onBookmark = (_homeSelected >= 3 && _homeSelected < 3 + (int)_bookmarks.size());
if (onBookmark)
bool onUrl = (_homeSelected == 1);
bool onSearch = (_homeSelected == 2);
if (onUrl)
snprintf(footerBuf, sizeof(footerBuf), "Tap:Enter URL Hold:Bk");
else if (onSearch)
snprintf(footerBuf, sizeof(footerBuf), "Tap:Search Hold:Bk");
else if (onBookmark)
snprintf(footerBuf, sizeof(footerBuf), "Swipe:Nav Tap:Go Hold:Del");
else
snprintf(footerBuf, sizeof(footerBuf), "Swipe:Nav Tap:Go");
snprintf(footerBuf, sizeof(footerBuf), "Swipe:Nav Tap:Go Hold:Bk");
#else
bool hasData = (_cookieCount > 0 || !_history.empty());
bool onBookmark = (_homeSelected >= 3 && _homeSelected < 3 + (int)_bookmarks.size());
@@ -3413,12 +3422,10 @@ private:
snprintf(linkBuf, sizeof(linkBuf), "#%d_ Ent:Go", _linkInput);
hint = linkBuf;
#if defined(LilyGo_T5S3_EPaper_Pro)
} else if (_formCount > 0 && _linkCount > 0) {
hint = "Swipe:Pg Hold:Bk";
} else if (_linkCount > 0) {
hint = "Swipe:Pg Hold:Bk";
hint = "Tap:Pg/Lnk Hold:Bk";
} else {
hint = "Swipe:Pg Hold:Bk";
hint = "Tap:Pg Hold:Bk";
}
#else
} else if (_formCount > 0 && _linkCount > 0) {
@@ -5237,6 +5244,33 @@ public:
return (_mode == IRC_CHAT && _ircComposing) ||
(_mode == IRC_SETUP && _ircSetupEditing);
}
// ---- Accessors for T5S3 touch mapping and VKB integration ----
int getHomeSelected() const { return _homeSelected; }
int getLinkCount() const { return _linkCount; }
int getBookmarkCount() const { return (int)_bookmarks.size(); }
const char* getUrlText() const { return _urlBuffer; }
// Set URL text and activate editing mode (for VKB submit)
void setUrlText(const char* text) {
strncpy(_urlBuffer, text, WEB_MAX_URL_LEN - 1);
_urlBuffer[WEB_MAX_URL_LEN - 1] = '\0';
_urlLen = strlen(_urlBuffer);
_urlEditing = true;
}
// Set search text and activate editing mode (for VKB submit)
void setSearchText(const char* text) {
strncpy(_searchBuffer, text, sizeof(_searchBuffer) - 1);
_searchBuffer[sizeof(_searchBuffer) - 1] = '\0';
_searchLen = strlen(_searchBuffer);
_searchEditing = true;
}
// Set WiFi password text (for VKB submit)
void setWifiPassText(const char* text) {
strncpy(_wifiPass, text, WEB_WIFI_PASS_LEN - 1);
_wifiPass[WEB_WIFI_PASS_LEN - 1] = '\0';
_wifiPassLen = strlen(_wifiPass);
}
// Returns true if a password reveal is active and needs a refresh after expiry
bool needsRevealRefresh() const {
if (_formLastCharAt > 0 && (millis() - _formLastCharAt) < 900) {

View File

@@ -29,7 +29,13 @@ enum VKBPurpose {
VKB_ADMIN_CLI, // Repeater admin CLI command
VKB_NOTES, // Insert text into notes
VKB_SETTINGS_NAME, // Edit node name
VKB_WIFI_PASSWORD // WiFi password entry (settings screen)
VKB_WIFI_PASSWORD, // WiFi password entry (settings screen)
#ifdef MECK_WEB_READER
VKB_WEB_URL, // Web reader URL entry
VKB_WEB_SEARCH, // Web reader DuckDuckGo search query
VKB_WEB_WIFI_PASS, // Web reader WiFi password
VKB_WEB_LINK, // Web reader link number entry
#endif
};
class VirtualKeyboard {