Add localization support for multi-language UI

This commit introduces comprehensive localization support for the application, enabling dynamic language switching and localized UI elements. Key changes include:

- Added `.resx` files for German (de-DE), English (en-US), and French (fr-FR).
- Updated Razor components to use `IStringLocalizer` for dynamic string localization.
- Introduced the `L(string key, string fallback)` helper method for consistent localized string retrieval with fallback support.
- Implemented dynamic culture initialization in `Program.cs` via an API call to `/api/Localization/lang`.
- Localized error pages, grid columns, tabs, popups, validation messages, and tooltips.
- Dynamically generated privacy policy links based on the current culture.
- Improved user experience with fully localized loading states, error handling, and UI labels.

These changes enhance accessibility and usability, making the application more user-friendly for a global audience.
This commit is contained in:
2026-09-28 10:46:06 +02:00
parent 48cfd3f416
commit 735f072dd1
13 changed files with 682 additions and 187 deletions

View File

@@ -1,14 +1,17 @@
@using EnvelopeGenerator.Server.Client.Services
@using EnvelopeGenerator.Application.Resources
@using Microsoft.Extensions.Localization
@rendermode InteractiveWebAssembly
@inject LocalizationService LocalizationService
@inject NavigationManager Navigation
@inject IStringLocalizer<Resource> UiLocalizer
<div class="sf-lang-combo">
<button type="button"
class="sf-lang-trigger"
@onclick="ToggleMenu"
aria-label="Language"
aria-label="@L("Language", "Language")"
aria-expanded="@_isOpen">
<span class="fi @_selected.FlagClass"></span>
</button>
@@ -17,11 +20,11 @@
{
<button type="button"
class="sf-lang-backdrop"
aria-label="Close language menu"
aria-label="@L("CloseLanguageMenu", "Close language menu")"
@onclick="CloseMenu">
</button>
<div class="sf-lang-menu" role="listbox" aria-label="Languages">
<div class="sf-lang-menu" role="listbox" aria-label="@L("Languages", "Languages")">
@foreach (var option in _options)
{
<button type="button"
@@ -81,4 +84,10 @@
}
private sealed record LanguageOption(string Code, string FlagClass, string ShortName);
string L(string key, string fallback)
{
var value = UiLocalizer[key];
return value.ResourceNotFound ? fallback : value.Value;
}
}