CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/npm-react-aria--i18n

Comprehensive internationalization support for React applications with locale-aware hooks and utilities

Pending

Quality

Pending

Does it follow best practices?

Impact

Pending

No eval scenarios have been run

Overview
Eval results
Files

number-list-formatting.mddocs/

Number and List Formatting

Numeric formatting and list presentation for different locales and cultural contexts with automatic locale updates and performance caching.

Capabilities

useNumberFormatter Hook

Provides localized number formatting for the current locale with support for currency, percentages, and custom number styles.

/**
 * Provides localized number formatting for the current locale. Automatically updates when the locale changes,
 * and handles caching of the number formatter for performance.
 * @param options - Formatting options from @internationalized/number
 * @returns Intl.NumberFormat instance
 */
function useNumberFormatter(options?: NumberFormatOptions): Intl.NumberFormat;

type NumberFormatOptions = Intl.NumberFormatOptions;

Usage Examples:

import { useNumberFormatter, I18nProvider } from "@react-aria/i18n";

// Basic number formatting
function NumberDisplay() {
  const formatter = useNumberFormatter();
  
  return <p>{formatter.format(1234567.89)}</p>;
  // US English: "1,234,567.89"
  // German: "1.234.567,89"
  // French: "1 234 567,89"
}

// Currency formatting
function CurrencyDisplay() {
  const formatter = useNumberFormatter({
    style: "currency",
    currency: "USD"
  });
  
  return <p>{formatter.format(1299.99)}</p>;
  // US English: "$1,299.99"
  // UK English: "US$1,299.99"
}

// Percentage formatting
function PercentageDisplay() {
  const formatter = useNumberFormatter({
    style: "percent",
    minimumFractionDigits: 1
  });
  
  return <p>{formatter.format(0.1534)}</p>;
  // "15.3%"
}

// Unit formatting
function UnitDisplay() {
  const formatter = useNumberFormatter({
    style: "unit",
    unit: "kilometer-per-hour",
    unitDisplay: "short"
  });
  
  return <p>{formatter.format(65)}</p>;
  // "65 km/h"
}

// Custom decimal and grouping options
function PrecisionNumberDisplay() {
  const formatter = useNumberFormatter({
    minimumFractionDigits: 2,
    maximumFractionDigits: 4,
    useGrouping: true
  });
  
  return <p>{formatter.format(1234.5)}</p>;
  // "1,234.50"
}

Intl.NumberFormat Methods

The Intl.NumberFormat provides additional methods for advanced formatting needs.

interface Intl.NumberFormat {
  /** Format a number to a string */
  format(value: number): string;
  /** Format a number to an array of parts with type information */
  formatToParts(value: number): Intl.NumberFormatPart[];
  /** Format a range between two numbers */
  formatRange(start: number, end: number): string;
  /** Format a range to parts */
  formatRangeToParts(start: number, end: number): Intl.NumberFormatPart[];
  /** Get resolved formatting options */
  resolvedOptions(): Intl.ResolvedNumberFormatOptions;
}

Advanced Usage Examples:

function AdvancedNumberFormatting() {
  const formatter = useNumberFormatter({
    style: "currency",
    currency: "EUR",
    minimumFractionDigits: 2
  });
  
  const value = 1234.56;
  const startValue = 100;
  const endValue = 200;
  
  return (
    <div>
      {/* Basic formatting */}
      <p>Price: {formatter.format(value)}</p>
      
      {/* Parts formatting for custom styling */}
      <p>
        Styled: {formatter.formatToParts(value).map((part, i) => (
          <span key={i} className={`number-${part.type}`}>
            {part.value}
          </span>
        ))}
      </p>
      
      {/* Range formatting */}
      <p>Range: {formatter.formatRange(startValue, endValue)}</p>
      
      {/* Resolved options */}
      <p>Currency: {formatter.resolvedOptions().currency}</p>
    </div>
  );
}

useListFormatter Hook

Provides localized list formatting for arrays with proper conjunction and disjunction support.

/**
 * Provides localized list formatting for the current locale. Automatically updates when the locale changes,
 * and handles caching of the list formatter for performance.
 * @param options - Formatting options for list presentation
 * @returns Intl.ListFormat instance
 */
function useListFormatter(options?: Intl.ListFormatOptions): Intl.ListFormat;

interface Intl.ListFormatOptions {
  /** The locale matching algorithm to use */
  localeMatcher?: "best fit" | "lookup";
  /** The type of list */
  type?: "conjunction" | "disjunction" | "unit";
  /** The style of the list */
  style?: "long" | "short" | "narrow";
}

Usage Examples:

import { useListFormatter, I18nProvider } from "@react-aria/i18n";

// Basic list formatting (conjunction - "and")
function BasicListDisplay() {
  const formatter = useListFormatter({
    style: "long",
    type: "conjunction"
  });
  
  const items = ["apples", "oranges", "bananas"];  
  return <p>{formatter.format(items)}</p>;
  // English: "apples, oranges, and bananas"
  // Spanish: "apples, oranges y bananas"
}

// Disjunction list formatting ("or")
function DisjunctionListDisplay() {
  const formatter = useListFormatter({
    style: "long",
    type: "disjunction"
  });
  
  const options = ["red", "blue", "green"];
  return <p>Choose: {formatter.format(options)}</p>;
  // English: "red, blue, or green"
}

// Unit list formatting (no conjunctions)
function UnitListDisplay() {
  const formatter = useListFormatter({
    style: "short",
    type: "unit"
  });
  
  const measurements = ["5 ft", "10 in"];
  return <p>{formatter.format(measurements)}</p>;
  // "5 ft, 10 in"
}

// Different styles comparison
function ListStyleComparison() {
  const longFormatter = useListFormatter({ style: "long" });
  const shortFormatter = useListFormatter({ style: "short" });
  const narrowFormatter = useListFormatter({ style: "narrow" });
  
  const items = ["first", "second", "third"];
  
  return (
    <div>
      <p>Long: {longFormatter.format(items)}</p>
      <p>Short: {shortFormatter.format(items)}</p>
      <p>Narrow: {narrowFormatter.format(items)}</p>
    </div>
  );
}

// Locale-specific list formatting
function LocaleSpecificLists() {
  const items = ["JavaScript", "TypeScript", "React"];
  
  return (
    <div>
      <I18nProvider locale="en-US">
        <ListDisplay items={items} />
      </I18nProvider>
      <I18nProvider locale="de-DE">
        <ListDisplay items={items} />
      </I18nProvider>
      <I18nProvider locale="ja-JP">
        <ListDisplay items={items} />
      </I18nProvider>
    </div>
  );
}

function ListDisplay({ items }: { items: string[] }) {
  const formatter = useListFormatter();
  return <p>{formatter.format(items)}</p>;
}

ListFormatter Methods

Additional methods available on the ListFormat instance.

interface Intl.ListFormat {
  /** Format an array of strings to a localized list string */
  format(list: string[]): string;
  /** Format an array to parts with type information */
  formatToParts(list: string[]): Intl.ListFormatPart[];
  /** Get resolved formatting options */
  resolvedOptions(): Intl.ResolvedListFormatOptions;
}

Advanced List Formatting:

function AdvancedListFormatting() {
  const formatter = useListFormatter({
    style: "long",
    type: "conjunction"
  });
  
  const items = ["red", "green", "blue"];
  
  return (
    <div>
      {/* Basic formatting */}
      <p>Colors: {formatter.format(items)}</p>
      
      {/* Parts formatting for custom styling */}
      <p>
        Styled: {formatter.formatToParts(items).map((part, i) => (
          <span key={i} className={`list-${part.type}`}>
            {part.value}
          </span>
        ))}
      </p>
      
      {/* Options inspection */}
      <p>Style: {formatter.resolvedOptions().style}</p>
    </div>
  );
}

Install with Tessl CLI

npx tessl i tessl/npm-react-aria--i18n

docs

context-locale.md

date-time-formatting.md

index.md

number-list-formatting.md

server-support.md

string-localization.md

tile.json