# useDirection
_(no submodules)_
## Purpose
`useDirection()` returns the writing direction (`'ltr'` / `'rtl'`) for
the active locale. Composes `useLocale` (so it inherits the underlying
`useSyncExternalStore` subscription) and runs the locale through
`@suaveplan/i18n`'s `getTextDirection` helper. The single-source-of-truth
for which locales are RTL lives in the i18n core's `RTL_LOCALES` set —
the React surface does not duplicate the list.
The hook is the canonical primitive for direction-sensitive UI: setting
``, mirroring icon strips, swapping margin-left for
margin-right in a CSS module, and so on. A locale change like
`setLocale('ar-AE')` flips the result to `'rtl'` on the same React
commit cycle as the bus emission, so the UI re-mirrors atomically with
the new translations.
## Features
- Returns `{ direction, locale }` — both kept in sync with the active locale.
- `'ltr'` / `'rtl'` resolution via the i18n core's `getTextDirection`.
- `direction` defaults to `'ltr'` on the production no-Provider fallback (the safer default for unknown locales).
- Memoised on the locale string so a no-op re-render does not re-call `getTextDirection`.
- Re-renders on `languageChanged` via the inherited `useLocale` subscription.
## Usage: Basic Example
```tsx
import { useDirection } from "@suaveplan/react-i18n";
export function ChatBubble(props: { readonly children: React.ReactNode }) {
const { direction } = useDirection();
return (
{props.children}
);
}
```
## Usage: Advanced Example
For document-level mirroring set the `` attribute from a
top-level effect that mirrors the hook's output. The pattern below
keeps the markup in sync without needing every component to be
direction-aware.
```tsx
import { useEffect } from "react";
import { useDirection } from "@suaveplan/react-i18n";
export function HtmlDirectionSync(): null {
const { direction, locale } = useDirection();
useEffect(() => {
const root = document.documentElement;
if (locale !== undefined) root.lang = locale;
root.dir = direction;
}, [direction, locale]);
return null;
}
```
## API Reference
### `useDirection(): UseDirectionReturn`
- **Returns**: `{ direction, locale }`.
- `direction: 'ltr' | 'rtl'` — derived from `getTextDirection(locale)`. Defaults to `'ltr'` when `locale === undefined`.
- `locale: string | undefined` — current active locale, mirrored from `useLocale().locale`.
- **Throws**: `ReactI18nError(REACT_I18N.NO_PROVIDER)` outside a `` in dev mode (inherited from `useLocale → useI18n`).
## Implementation Notes
- The lookup is wrapped in `useMemo` keyed on the locale string. `getTextDirection` is cheap (a single `Set.has` after a string split), but the memo also keeps the returned object reference stable across re-renders that did not change the locale, which keeps `React.memo`-wrapped descendants from re-rendering.
- The hook deliberately delegates the RTL list to `@suaveplan/i18n` instead of duplicating it. New RTL scripts added to the upstream `RTL_LOCALES` table propagate automatically — no React-side maintenance required.
- The fallback to `'ltr'` on the no-Provider production path matches the broader package contract: end-users see degraded but non-broken UI when configuration is missing.