From 6c3fdf30cfedea7913bdede34a2448e36ddfcd32 Mon Sep 17 00:00:00 2001 From: Garry Tan Date: Sun, 29 Mar 2026 23:37:28 -0700 Subject: [PATCH] fix: disable action buttons when disconnected, no error spam - setActionButtonsEnabled() toggles .disabled class on all cleanup/screenshot buttons (both chat toolbar and inspector toolbar) - Called with false in updateConnection when server URL is null - Called with true when connection established - runCleanup/runScreenshot silently return when disconnected instead of showing 'Not connected' error notifications - CSS .disabled style: pointer-events:none, opacity:0.3, cursor:not-allowed Co-Authored-By: Claude Opus 4.6 (1M context) --- extension/sidepanel.css | 6 ++++++ extension/sidepanel.js | 13 +++++++++++-- 2 files changed, 17 insertions(+), 2 deletions(-) diff --git a/extension/sidepanel.css b/extension/sidepanel.css index 8c01d41e..2cc94a0f 100644 --- a/extension/sidepanel.css +++ b/extension/sidepanel.css @@ -627,6 +627,12 @@ body::after { transform: scale(0.96); } +.quick-action-btn.disabled, .inspector-action-btn.disabled { + pointer-events: none; + opacity: 0.3; + cursor: not-allowed; +} + .quick-action-btn.loading { pointer-events: none; opacity: 0.5; diff --git a/extension/sidepanel.js b/extension/sidepanel.js index 81438ff2..a1f13180 100644 --- a/extension/sidepanel.js +++ b/extension/sidepanel.js @@ -1153,7 +1153,7 @@ inspectorSendBtn.addEventListener('click', () => { async function runCleanup(...buttons) { if (!serverUrl || !serverToken) { - addChatEntry({ type: 'notification', message: 'Not connected to browse server' }); + // Don't spam errors, buttons should already be disabled return; } buttons.forEach(b => b?.classList.add('loading')); @@ -1181,7 +1181,6 @@ async function runCleanup(...buttons) { async function runScreenshot(...buttons) { if (!serverUrl || !serverToken) { - addChatEntry({ type: 'notification', message: 'Not connected to browse server' }); return; } buttons.forEach(b => b?.classList.add('loading')); @@ -1263,6 +1262,14 @@ function connectInspectorSSE() { // ─── Server Discovery ─────────────────────────────────────────── +function setActionButtonsEnabled(enabled) { + const btns = document.querySelectorAll('.quick-action-btn, .inspector-action-btn'); + btns.forEach(btn => { + btn.disabled = !enabled; + btn.classList.toggle('disabled', !enabled); + }); +} + function updateConnection(url, token) { const wasConnected = !!serverUrl; serverUrl = url; @@ -1272,6 +1279,7 @@ function updateConnection(url, token) { const port = new URL(url).port; document.getElementById('footer-port').textContent = `:${port}`; setConnState('connected'); + setActionButtonsEnabled(true); connectSSE(); connectInspectorSSE(); if (chatPollInterval) clearInterval(chatPollInterval); @@ -1284,6 +1292,7 @@ function updateConnection(url, token) { } else { document.getElementById('footer-dot').className = 'dot'; document.getElementById('footer-port').textContent = ''; + setActionButtonsEnabled(false); if (chatPollInterval) { clearInterval(chatPollInterval); chatPollInterval = null; } if (tabPollInterval) { clearInterval(tabPollInterval); tabPollInterval = null; } if (wasConnected) {