PhoenixKitWeb.Components.Core.LanguageSwitcher (phoenix_kit v1.7.118)

Copy Markdown View Source

Language switcher component for frontend and admin applications.

Provides reusable language selection UI that pulls available languages from the unified Languages module. Three display variants are available: dropdown, button group, and inline.

Continent Grouping

When more than 7 languages are enabled (configurable via continent_threshold), the dropdown automatically shows a two-step interface: first pick a continent, then pick a language within it. Set group_by_continent={false} to always show a flat list regardless of language count.

Examples

# Basic dropdown — auto-groups by continent when >7 languages
<.language_switcher_dropdown current_locale={@current_locale} />

# Force flat list (no continent step)
<.language_switcher_dropdown current_locale={@current_locale} group_by_continent={false} />

# Custom threshold for continent grouping
<.language_switcher_dropdown current_locale={@current_locale} continent_threshold={5} />

# Show current language in trigger button
<.language_switcher_dropdown current_locale={@current_locale} show_current={true} />

# Button group (for mobile)
<.language_switcher_buttons current_locale={@current_locale} />

# Inline text links (for footers)
<.language_switcher_inline current_locale={@current_locale} />

Summary

Functions

Overrides each language entry's :name (or "name") with the bare base-language label when only one dialect of that base is configured. Multi-dialect bases keep their full configured name so users can tell them apart.

Strips the country / region qualifier from a configured language name. Used to render bare base-language labels when only one dialect of the base is enabled.

Renders a button group language switcher.

Renders a dropdown language switcher.

Renders an inline language switcher.

Functions

dedupe_names(languages)

Overrides each language entry's :name (or "name") with the bare base-language label when only one dialect of that base is configured. Multi-dialect bases keep their full configured name so users can tell them apart.

Accepts a list of language entries shaped as atom-keyed maps, string-keyed maps, or %PhoenixKit.Modules.Languages.Language{} structs. Returns the list in the same shape with the relevant :name/"name" key replaced.

Used by the admin top-bar dropdown and the user dashboard nav to inherit the frontend switcher's dedup rule without duplicating the logic. Internal frontend-switcher code paths (build_dialect_list/1, langs_to_dialect_maps/2) compute names inline because they emit a new result map per entry; this helper is the entry point for callers that already have a list of entries and just need their names normalized.

extract_base_language_name(full_name)

Strips the country / region qualifier from a configured language name. Used to render bare base-language labels when only one dialect of the base is enabled.

Public because the admin top-bar dropdown (PhoenixKitWeb.Components.AdminNav) and the user dashboard nav (PhoenixKitWeb.Components.UserDashboardNav) both call into it via dedupe_names/1 so all language menus share one rule.

Examples

iex> extract_base_language_name("Spanish (Mexico)")
"Spanish"

iex> extract_base_language_name("Chinese (Simplified)")
"Chinese"

iex> extract_base_language_name("Japanese")
"Japanese"

language_switcher_buttons(assigns)

Renders a button group language switcher.

Displays language buttons in a row. Good for mobile layouts and areas where space allows for multiple buttons. Automatically fetches the configured languages (or default top 12 if not configured).

Examples

<.language_switcher_buttons current_locale={@current_locale} />

Attributes

  • current_locale (:string) - Current active language code (auto-detected if not provided). Defaults to nil.
  • languages (:any) - List of language maps. If nil, fetches from Language Module. Defaults to nil.
  • show_flags (:boolean) - Show language flags. Defaults to true.
  • show_names (:boolean) - Show language names. Defaults to true.
  • goto_home (:boolean) - Redirect to home page on language switch. Defaults to false.
  • hide_current (:boolean) - Hide currently selected language from list. Defaults to false.
  • class (:string) - Additional CSS classes. Defaults to "".
  • current_path (:string) - Current path to preserve when switching languages. Defaults to nil.
  • per_translation_urls (:list) - Optional per-translation URL overrides. See language_switcher_dropdown/1 for details. Defaults to nil.

language_switcher_dropdown(assigns)

Renders a dropdown language switcher.

Displays a globe icon that opens a dropdown menu with available languages. Automatically fetches the configured languages (or defaults when unconfigured). Used in both frontend navigation bars and the admin panel header.

When more than continent_threshold languages are enabled, shows a two-step continent → language navigation. Set group_by_continent={false} to disable.

Examples

<.language_switcher_dropdown current_locale={@current_locale} />

<.language_switcher_dropdown
  current_locale={@current_locale}
  group_by_continent={false}
/>

Attributes

  • current_locale (:string) - Current active language code (auto-detected if not provided). Defaults to nil.

  • languages (:any) - List of language maps. If nil, fetches from Language Module. Defaults to nil.

  • show_flags (:boolean) - Show language flags. Defaults to true.

  • show_names (:boolean) - Show language names. Defaults to true.

  • show_native_names (:boolean) - Show native language names. Defaults to false.

  • goto_home (:boolean) - Redirect to home page on language switch. Defaults to false.

  • hide_current (:boolean) - Hide currently selected language from list. Defaults to false.

  • class (:string) - Additional CSS classes. Defaults to "".

  • current_path (:string) - Current path to preserve when switching languages. Defaults to nil.

  • scroll_threshold (:integer) - Number of languages after which to show scrollbar and search. Defaults to 10.

  • show_current (:boolean) - Show current language (flag + name) in dropdown trigger instead of globe icon. Defaults to false.

  • group_by_continent (:boolean) - Enable continent grouping when language count exceeds continent_threshold. Defaults to true.

  • continent_threshold (:integer) - Number of languages after which the continent grouping step is shown. Defaults to 7.

  • _language_update_key (:any) - Internal: forces re-render when languages change. Defaults to nil.

  • per_translation_urls (:list) - Optional list of per-translation URLs that override the locale-rewrite default. Each entry is %{code: <display_code>, url: <full_url>}. Both atom-keyed (%{code: ..., url: ...}) and string-keyed (%{"code" => ..., "url" => ...}) entries are accepted — useful when the list comes from JSON/JSONB rather than Elixir code.

    Useful when a feature module (e.g. phoenix_kit_publishing) has computed canonical URLs for each available translation that the simple locale-rewrite default can't reproduce — for example when a post has per-language URL slugs. Pass assigns[:phoenix_kit_publishing_translations] from the layout; the switcher resolves each language's base_code against the list (via DialectMapper.extract_base/1) and falls back to the locale-rewrite URL when no entry matches or the matched entry has a nil url (e.g. an unpublished draft).

    Defaults to nil.

  • ai_translate (:map) - Optional opt-in for the AI-translate affordance. When present and :enabled is true, missing-language items show a sparkle button that fires the host LV's phx-click event (and a bulk "translate all missing" CTA renders below the list when ≥2 languages are missing).

    Shape:

    %{
      enabled: true,
      event: "translate_lang",        # phx-click target on host LV
      missing: ["es", "de"],          # base codes lacking a translation
      in_flight: ["es"]               # show spinner, click disabled
    }

    Only :missing and :in_flight drive rendering. A "completed" language is signalled simply by the host dropping its code from :missing — the sparkle then disappears on the next render. (There is no separate :completed checkmark state; pass nothing for it.)

    The component emits the host's event; the host owns enqueuing the actual translation worker and broadcasting the resulting :missing / :in_flight state back via PubSub. Set :enabled to false (or pass nil) to fall back to today's behavior with no AI UI — convenient for hosts that gate on PhoenixKit.Modules.AI.available?/0.

    Bulk action dispatch

    The "Translate all missing" CTA fires the same event with phx-value-lang="*" as a sentinel. Host handlers branch on the value:

    def handle_event("translate_lang", %{"lang" => "*"}, socket) do
      # enqueue one job per *actionable* language (missing minus
      # in_flight) — matches the count shown on the bulk button
    end
    
    def handle_event("translate_lang", %{"lang" => lang}, socket) do
      # enqueue a single-language job
    end

    Defaults to nil.

language_switcher_inline(assigns)

Renders an inline language switcher.

Displays languages as inline text links. Minimal design perfect for footers or compact navigation areas. Automatically fetches the configured languages (or default top 12 if not configured).

Examples

<.language_switcher_inline current_locale={@current_locale} />

Attributes

  • current_locale (:string) - Current active language code (auto-detected if not provided). Defaults to nil.
  • languages (:any) - List of language maps. If nil, fetches from Language Module. Defaults to nil.
  • show_flags (:boolean) - Show language flags. Defaults to true.
  • show_names (:boolean) - Show language names. Defaults to true.
  • goto_home (:boolean) - Redirect to home page on language switch. Defaults to false.
  • hide_current (:boolean) - Hide currently selected language from list. Defaults to false.
  • class (:string) - Additional CSS classes. Defaults to "".
  • current_path (:string) - Current path to preserve when switching languages. Defaults to nil.
  • per_translation_urls (:list) - Optional per-translation URL overrides. See language_switcher_dropdown/1 for details. Defaults to nil.