1dc2eab0cf
- vue-i18n 11 with the Composition API: English comes with the page, any other language loads the first time it is needed from screen_manager/translations, and a text a language lacks shows in English. The build keeps only _meta and editor of each file (vite.config.ts), never the screens' or the add-on's texts. - The editor follows the language of the user's Home Assistant profile (<html lang> of Home Assistant's page), else the browser's; plural forms follow the file's _meta.plural, with the screens' rules. - Every request tells the add-on the editor's language (X-ESP-Screens-Language), so its own words can follow it. - The mockup draws the screens' words (Unavailable, Page 2 ›, the date, "5 min ago") in the screens' language, with their clock and number format. - Settings → Language & region: the screen language, time format and number format for every screen, with the user's own profile offered when it differs. The per-screen clock choice goes; the top bar points there. A screen that still needs the new language says so in its update badge. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
39 lines
1.4 KiB
Python
39 lines
1.4 KiB
Python
"""The editor's source, for the tests that read it.
|
|
|
|
The page is a Vue app in web/ (app 0.2.73); `npm run build` writes it to screen_manager/app/static. Tests look at
|
|
the source, not the build: every .ts and .vue file under web/src as one text (SCRIPT, which is also the markup:
|
|
a .vue file carries its template), and the stylesheets as another (CSS). Its English words are in the `editor` section
|
|
of screen_manager/translations/en.json since app 0.2.90: text() reads one of them.
|
|
"""
|
|
import json
|
|
from pathlib import Path
|
|
|
|
ROOT = Path(__file__).resolve().parents[1]
|
|
WEB = ROOT / 'web/src'
|
|
STATIC = ROOT / 'screen_manager/app/static'
|
|
|
|
FILES = sorted(p for p in WEB.rglob('*') if p.suffix in ('.ts', '.vue'))
|
|
SCRIPT = '\n'.join(p.read_text() for p in FILES)
|
|
PAGE = SCRIPT
|
|
CSS = '\n'.join(p.read_text() for p in sorted(WEB.glob('styles/*.css')))
|
|
|
|
|
|
def source(name):
|
|
"""One file by name, e.g. 'store.ts' or 'components/Sidebar.vue'."""
|
|
return (WEB / name).read_text()
|
|
|
|
|
|
def component(name):
|
|
return source(f'components/{name}.vue')
|
|
|
|
|
|
TEXTS = json.loads((ROOT / 'screen_manager/translations/en.json').read_text(encoding='utf-8'))['editor']
|
|
|
|
|
|
def text(key):
|
|
"""One English text of the editor by its key under `editor`, e.g. 'empty.choose.title'."""
|
|
node = TEXTS
|
|
for part in key.split('.'):
|
|
node = node[int(part)] if isinstance(node, list) else node[part]
|
|
return node
|