Files
zeekay db82b38d02 Corner: Help and Preferences in the bottom corner of every site page
@hanzo/ui's Corner, mounted once (components/shell/help.tsx): Get help
(/support), Docs (docs.hanzo.ai, a new tab) and Contact us (/contact),
then Theme and Language. It sits at the start corner, so Arabic puts it
bottom-right. No Currency row: hanzo.ai bills in US dollars only.

Language is lib/language.ts, now in Corner's shape: @hanzo/i18n's
registry less the locales waiting for review, each in its own script
with its English name to search by, and the i18n setter, which sets
<html lang dir>.

Not drawn in the app: the rooms and the app at /, /dev and /studio keep
the account at the rail's foot, bottom-left, and their Settings holds
the preferences there. /dashboard joins the rooms' table. Not drawn
while the cookie banner asks, so the two never share the foot. /start's
composer band now clears the start side on a phone, where it cleared
the end for the help mark removed earlier, and the corner mounts after
the page so it paints over that band.

Gate: e2e/gates/help.spec.ts.
2026-10-22 13:05:18 -07:00

32 lines
1.5 KiB
TypeScript

/**
* The languages hanzo.ai offers, as the corner control (@hanzo/ui `Corner`,
* components/shell/help.tsx) lists them, and the reader's choice among them.
*
* The registry is @hanzo/i18n's: each language named in its own script, never a
* flag, with its English name as the quieter second name a search also matches
* (`German` finds Deutsch) and the direction its script runs. The offer is the
* one its `LanguagePicker` makes (Settings → General): every locale but those
* waiting for a native reader (`review`), and the reader's own language whatever
* it is, since a choice made is kept. One rule for both, so the corner and the
* picker cannot come to offer different languages.
*
* The choice is `useI18n()`'s, mounted once in app/providers.tsx (`Language`):
* choosing sets the document's `lang` and `dir` and keeps the choice with the
* person.
*/
import { locales } from '@hanzo/i18n'
import { useI18n } from '@hanzo/i18n/react'
import type { Option, Setting } from '@hanzo/ui/corner'
/** The languages offered to a reader whose language is `current`. */
export const offered = (current: string): Option[] =>
locales
.filter((l) => !l.review || l.code === current)
.map(({ code, name, englishName, dir }) => ({ code, label: name, hint: englishName, dir }))
/** The corner's language row, controlled by the host: what is chosen, what may be, and how to choose. */
export function useLanguage(): Setting {
const { locale, setLocale } = useI18n()
return { value: locale, options: offered(locale), onChange: setLocale }
}