From 56c0e6046258c2ffd041e753e8b82303815b9f57 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D1=82=D0=BE=D0=BD=20=D0=A2=D1=80=D0=BE=D1=88?= =?UTF-8?q?=D0=B8=D0=BD?= Date: Sat, 12 Sep 2026 19:55:14 +0300 Subject: [PATCH] ui: tooltip on the status dot shows the server state - the dot carries its own title (Connecting... / No server connection), matching the wrapper tooltip; it is cleared when the sim icons replace the dot - tests assert the dot title in both server states and its removal once the server is up; SW cache v110 -> v111. --- frontend/index.html | 7 +++++-- frontend/sw.js | 2 +- frontend/tests/indicator.test.js | 4 ++++ 3 files changed, 10 insertions(+), 3 deletions(-) diff --git a/frontend/index.html b/frontend/index.html index a659fd6..d3790b1 100644 --- a/frontend/index.html +++ b/frontend/index.html @@ -21,7 +21,7 @@

OTAMan SIM OTA with a Human Face v2.0.0

- + @@ -4406,16 +4406,19 @@ function pysimUpdateStateIndicator() { if (_pysimServerAvailable === true) { const state = pysimAvailabilityState(); dot.classList.add('hidden'); + dot.removeAttribute('title'); img.classList.remove('hidden'); img.src = _pysimEquipping ? 'sim_anim.svg' : (state === 'card' ? 'sim.svg' : 'nosim.svg'); el.setAttribute('title', _pysimEquipping ? t('Card inserted — initializing...') : (state === 'card' ? t('Card equipped') : t('Server connected, no card equipped'))); } else { + const serverState = _pysimServerAvailable === false ? t('No server connection') : t('Connecting...'); img.classList.add('hidden'); dot.classList.remove('hidden'); dot.classList.remove('text-red-500', 'text-gray-400'); dot.classList.add(_pysimServerAvailable === false ? 'text-red-500' : 'text-gray-400'); - el.setAttribute('title', _pysimServerAvailable === false ? t('No server connection') : t('Connecting...')); + dot.setAttribute('title', serverState); + el.setAttribute('title', serverState); } } diff --git a/frontend/sw.js b/frontend/sw.js index c282149..021bca4 100644 --- a/frontend/sw.js +++ b/frontend/sw.js @@ -1,4 +1,4 @@ -const CACHE = 'otaman-v110'; +const CACHE = 'otaman-v111'; const URLS = [ 'index.html', 'help.html', diff --git a/frontend/tests/indicator.test.js b/frontend/tests/indicator.test.js index f06afcb..b832d4c 100644 --- a/frontend/tests/indicator.test.js +++ b/frontend/tests/indicator.test.js @@ -38,6 +38,7 @@ function fakeEl() { contains: c => classes.has(c), }, setAttribute(k, v) { this.attrs[k] = v; }, + removeAttribute(k) { delete this.attrs[k]; }, }; } @@ -63,6 +64,7 @@ test('unprobed server shows a gray dot and a Connecting title', () => { assert.ok(!dot.classes.has('hidden')); assert.ok(img.classes.has('hidden')); assert.strictEqual(wrap.attrs.title, 'Connecting...'); + assert.strictEqual(dot.attrs.title, 'Connecting...'); }); test('unreachable server shows a red dot', () => { @@ -74,6 +76,7 @@ test('unreachable server shows a red dot', () => { assert.ok(!dot.classes.has('text-gray-400')); assert.ok(img.classes.has('hidden')); assert.strictEqual(wrap.attrs.title, 'No server connection'); + assert.strictEqual(dot.attrs.title, 'No server connection'); }); test('server up without a card shows nosim.svg', () => { @@ -85,6 +88,7 @@ test('server up without a card shows nosim.svg', () => { assert.ok(!img.classes.has('hidden')); assert.strictEqual(img.src, 'nosim.svg'); assert.strictEqual(wrap.attrs.title, 'Server connected, no card equipped'); + assert.strictEqual(dot.attrs.title, undefined); }); test('equipped card shows sim.svg', () => {