Languages and right to left
Components speak the language of the page: the nearest lang attribute, or <html lang>. Their own text (button names, announcements, counts) comes from message catalogs, dates and numbers from Intl, and every layout mirrors under dir="rtl".
Set the language
Components use the nearest lang attribute above them, through shadow roots, and re-render when <html lang> or <html dir> changes. Dates, numbers and the first day of the week follow it even before any catalog is loaded.
<html lang="de">
<section lang="ar" dir="rtl">…</section>>Load translations
English is built in. @lit-material/translations has Arabic, German, Spanish, French, Japanese, Polish and Ukrainian, one module each, so you ship only the ones you import.
import { registerTranslation } from "@lit-material/core/localize.js";
import de from "@lit-material/translations/de.js";
import ar from "@lit-material/translations/ar.js";
registerTranslation(de, ar);
A missing language or message falls back to the base language (de for de-AT), then to English. Register the same $code again to change single messages: registerTranslation({ $code: "en", "alert.dismiss": "Close" }).
Counts and placeholders
Messages are text with {name} placeholders; numbers in them are formatted for the language. Counts are plural objects chosen through Intl.PluralRules, so Polish gets its few and many forms and Arabic all six.
"diff.unchangedLines": { one: "{count} unchanged line", other: "{count} unchanged lines" }
To add a language, start from the en catalog and type yours with satisfies Catalog: TypeScript then fails when a component adds a message you haven't translated.
Right to left
Set dir="rtl" on <html> or any container. Layout uses logical CSS properties; tabs, radio groups, segmented buttons, steppers, date grids, trees and carousels flip their arrow keys; menus, popovers and selects open from the start edge; chevrons and other directional icons mirror. Code, clock dials and a line chart's time axis stay left to right, as they read the same way in every language.
Your app's own text
The catalogs cover the components' text. For your own strings use @lit/localize, or register keys of your own and read them with a LocalizeController: this.localize.term("app.greeting", "Hello").
Server rendering
On the server there's no page to read <html lang> from: put lang on the element or call setFallbackLocale() before rendering, so the server's text matches the browser's when it hydrates.