fix locale

This commit is contained in:
2025-12-09 04:09:33 +08:00
parent 429fb39140
commit 24512412e5
7 changed files with 230 additions and 89 deletions

View File

@@ -1,23 +1,101 @@
@using Microsoft.AspNetCore.Components.Routing
@inject Atomx.Admin.Client.Services.ILocalizationProvider LocalizationProvider
@inject NavigationManager Navigation
<Router AppAssembly="typeof(Program).Assembly">
<Found Context="routeData">
<CascadingValue Value="routeData">
<AuthorizeRouteView RouteData="routeData" DefaultLayout="typeof(Layout.MainLayout)">
<NotAuthorized>
<RedirectToLogin />
</NotAuthorized>
</AuthorizeRouteView>
</CascadingValue>
<FocusOnNavigate RouteData="routeData" Selector="h1" />
</Found>
</Router>
<div @key="LocalizationProvider.CurrentCulture">
<Router AppAssembly="typeof(Program).Assembly">
<Found Context="routeData">
<CascadingValue Value="routeData">
<AuthorizeRouteView RouteData="routeData" DefaultLayout="typeof(Layout.MainLayout)">
<NotAuthorized>
<RedirectToLogin />
</NotAuthorized>
</AuthorizeRouteView>
</CascadingValue>
<FocusOnNavigate RouteData="routeData" Selector="h1" />
</Found>
</Router>
</div>
<AntContainer />
@code {
private bool _initialized;
protected override async Task OnInitializedAsync()
{
// Subscribe to language changes to remount router when needed
if (LocalizationProvider != null)
{
LocalizationProvider.LanguageChanged += OnLanguageChanged;
}
// Subscribe to navigation events so client-side nav to /zh/... or /en/... triggers culture change
Navigation.LocationChanged += OnLocationChanged;
// Try detect first URL segment as short culture (e.g. /zh/ or /en/) and set culture before first render
try
{
var relative = Navigation.ToBaseRelativePath(Navigation.Uri).Trim('/');
var segments = string.IsNullOrEmpty(relative) ? Array.Empty<string>() : relative.Split('/', StringSplitOptions.RemoveEmptyEntries);
var first = segments.FirstOrDefault();
var mapping = new Dictionary<string, string>(StringComparer.OrdinalIgnoreCase)
{
{ "zh", "zh-Hans" },
{ "en", "en-US" }
};
if (!string.IsNullOrEmpty(first) && mapping.TryGetValue(first, out var mapped))
{
try
{
if (OperatingSystem.IsBrowser())
{
await LocalizationProvider.SetCultureAsync(mapped);
}
else
{
if (LocalizationProvider is Atomx.Admin.Client.Services.LocalizationProvider concrete)
{
concrete.SetCultureForServer(mapped);
}
}
}
catch { }
}
}
catch { }
}
private async void OnLocationChanged(object? sender, LocationChangedEventArgs args)
{
try
{
var relative = Navigation.ToBaseRelativePath(args.Location).Trim('/');
var segments = string.IsNullOrEmpty(relative) ? Array.Empty<string>() : relative.Split('/', StringSplitOptions.RemoveEmptyEntries);
var first = segments.FirstOrDefault();
if (string.IsNullOrEmpty(first)) return;
var mapping = new Dictionary<string, string>(StringComparer.OrdinalIgnoreCase)
{
{ "zh", "zh-Hans" },
{ "en", "en-US" }
};
if (mapping.TryGetValue(first, out var mapped))
{
// if culture already set to same, skip
if (string.Equals(LocalizationProvider.CurrentCulture, mapped, StringComparison.OrdinalIgnoreCase)) return;
// Call async set; ignore errors
await LocalizationProvider.SetCultureAsync(mapped);
// Trigger router remount via StateHasChanged
_ = InvokeAsync(StateHasChanged);
}
}
catch { }
}
protected override async Task OnAfterRenderAsync(bool firstRender)
{
if (firstRender && !_initialized)
@@ -33,4 +111,19 @@
catch { }
}
}
private void OnLanguageChanged(object? s, string culture)
{
// Remount router via @key by triggering StateHasChanged
_ = InvokeAsync(StateHasChanged);
}
public void Dispose()
{
if (LocalizationProvider != null)
{
LocalizationProvider.LanguageChanged -= OnLanguageChanged;
}
Navigation.LocationChanged -= OnLocationChanged;
}
}