bible-strong-avatar-lab/src/i18n/__tests__/i18n-test.ts
Eric Cappannelli 99300b3b30 feat(runtime): ship semantic avatar packages and Studio export
- add the v1 AvatarDefinition schema, bounded parser, strict validation, semantic catalog, pure geometry, scene generation, and deterministic playback to @bible-strong/avatar-core
- add the React 19 renderer with semantic controls, SSR-safe embedded/floating layouts, direct frame updates, pointer and keyboard movement, constraints, callbacks, and accessible controls
- add real tarball packaging and a clean React/Vite consumer using the exported Strobi definition
- add Studio semantic-key authoring, runtime readiness, JSON download/copy, bundled-key recovery, concise errors, targeted local-project clearing, npm guidance, syntax highlighting, and a runnable package preview
- preserve the historical ZIP and Studio project exports, regenerate the standalone engine, and synchronize English, French, and Simplified Chinese copy
- add focused contract, playback, renderer, interaction, persistence, export, and localization coverage
- archive the completed runtime and semantic-curation specs, retain the Vite performance draft, and record the engineering session in TIMELOG.md

Validation:
- pnpm check: 19 test files, 162 tests, typecheck, engine freshness, package builds, and Studio production build passed
- npm pack dry runs: 30 core files and 10 React files
- package smoke: real tarballs installed, typechecked, and built outside the workspace
- browser checks: semantic playback, embedded/floating render, drag, mobile overflow, runtime export recovery, formatted copy, syntax colors, and live package preview

Publication remains disabled: both packages stay private and AGPL-3.0-only pending licensing and repository metadata approval. Vue and Angular adapters remain deferred.
2026-08-16 10:18:39 +02:00

90 lines
4.5 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import { translateStudioText } from '@/i18n'
describe('avatar studio translations', () => {
it('uses English for static interface copy', () => {
expect(translateStudioText('Couleur des yeux', 'en')).toBe('Eye color')
})
it('translates dynamic editor labels', () => {
expect(translateStudioText('Modifier l’expression 08', 'en')).toBe('Edit expression 08')
expect(translateStudioText('Sphère · porte les yeux', 'en')).toBe('Sphere · carries the eyes')
expect(translateStudioText('Cône 1 copie', 'en')).toBe('Cone 1 copy')
})
it('keeps the original French copy in French', () => {
expect(translateStudioText('Nouvel avatar', 'fr')).toBe('Nouvel avatar')
expect(translateStudioText('sleeping', 'fr')).toBe('sommeil')
})
it('translates the studio interface and dynamic labels to Simplified Chinese', () => {
expect(translateStudioText('Couleur des yeux', 'zh-CN')).toBe('眼睛颜色')
expect(translateStudioText('Modifier l’expression 08', 'zh-CN')).toBe('编辑表情 08')
expect(translateStudioText('sleeping', 'zh-CN')).toBe('睡眠')
})
it('translates every Photo Mode control to Simplified Chinese', () => {
expect(translateStudioText('Mode photo', 'zh-CN')).toBe('照片模式')
expect(translateStudioText('Dégradé radial', 'zh-CN')).toBe('径向渐变')
expect(translateStudioText('Définition du mode photo', 'zh-CN')).toBe('照片模式分辨率')
expect(translateStudioText('Télécharger en PNG', 'zh-CN')).toBe('下载 PNG')
expect(translateStudioText('Prendre une photo', 'zh-CN')).toBe('拍照')
expect(translateStudioText('Format d’export', 'zh-CN')).toBe('导出格式')
})
it('keeps runtime-export authoring copy synchronized in all three languages', () => {
expect(translateStudioText('Clé sémantique', 'fr')).toBe('Clé sémantique')
expect(translateStudioText('Clé sémantique', 'en')).toBe('Semantic key')
expect(translateStudioText('Clé sémantique', 'zh-CN')).toBe('语义键')
expect(translateStudioText('Exporter le JSON runtime', 'en')).toBe('Export runtime JSON')
expect(translateStudioText('Exporter le JSON runtime', 'zh-CN')).toBe('导出运行时 JSON')
expect(translateStudioText('Nouveau', 'en')).toBe('New')
expect(translateStudioText('Nouveau', 'zh-CN')).toBe('新增')
expect(translateStudioText('Démarrage rapide npm', 'en')).toBe('npm quick start')
expect(translateStudioText('Démarrage rapide npm', 'zh-CN')).toBe('npm 快速开始')
expect(translateStudioText('Lancer l’exemple', 'en')).toBe('Run example')
expect(translateStudioText('Lancer l’exemple', 'zh-CN')).toBe('运行示例')
expect(
translateStudioText(
'Exporte le fichier .avatar.json utilisé par les nouveaux packages npm.',
'en'
)
).toBe('Export the .avatar.json file used by the new npm packages.')
expect(
translateStudioText(
'Génère l’export ZIP autonome React ou JavaScript qui existait déjà.',
'zh-CN'
)
).toBe('生成原有的 React 或 JavaScript 独立 ZIP 导出。')
expect(translateStudioText('Export runtime incomplet', 'en')).toBe(
'Runtime export is incomplete'
)
expect(translateStudioText('Export runtime incomplet', 'zh-CN')).toBe('运行时导出不完整')
expect(translateStudioText('Effacer le projet local et recharger', 'en')).toBe(
'Clear local project and reload'
)
expect(translateStudioText('Effacer le projet local et recharger', 'zh-CN')).toBe(
'清除本地项目并重新加载'
)
expect(translateStudioText('Copier le JSON formaté', 'en')).toBe('Copy formatted JSON')
expect(translateStudioText('Copier le JSON formaté', 'zh-CN')).toBe('复制格式化的 JSON')
expect(translateStudioText('JSON runtime copié dans le presse-papiers.', 'en')).toBe(
'Runtime JSON copied to the clipboard.'
)
expect(translateStudioText('JSON runtime copié dans le presse-papiers.', 'zh-CN')).toBe(
'运行时 JSON 已复制到剪贴板。'
)
})
it('covers every configured state description in English', () => {
expect(translateStudioText('Rythme régulier et expressions concentrées.', 'en')).toBe(
'Steady rhythm and focused expressions.'
)
expect(translateStudioText('Grandes expressions et transitions rapides.', 'en')).toBe(
'Big expressions and fast transitions.'
)
expect(translateStudioText('Inclinaisons et forte asymétrie.', 'en')).toBe(
'Tilts and strong asymmetry.'
)
})
})