Files
SteUP_Dotnet/SteUp.Shared/Components/Pages/LoginPage.razor
T
MarcoE e3c9880d86 Porta l'accento sul bottone di accesso
"Accedi" era navy come l'ancora della struttura. E' l'unica azione della
schermata: porta l'accento come ogni azione primaria dell'app, e il navy resta
al testo e alla cornice.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-17 15:02:08 +02:00

146 lines
5.5 KiB
Plaintext

@page "/login"
@using Microsoft.Extensions.Logging
@using SteUp.Shared.Core.BarcodeReader.Contracts
@using SteUp.Shared.Core.Interface.System
@using SteUp.Shared.Core.Services
@inject IUserAccountService UserAccountService
@inject AppAuthenticationStateProvider AuthenticationStateProvider
@inject IGenericSystemService GenericSystemService
@inject IBarcodeManager BarcodeManager
@inject ILogger<LoginPage> Logger
@*
Accesso (STILE_UI §7): stessa struttura dell'app, registro diverso.
L'accento resta dove sta sempre, sull'unica azione della schermata.
*@
<div class="onboarding">
<form class="onboarding__panel" @onsubmit="SignInUser" @onsubmit:preventDefault="true">
<img src="_content/SteUp.Shared/images/logo_steup.svg" class="onboarding__logo" alt="SteUP"/>
@* Un solo pannello con tre righe divise da una linea, come le liste
del resto dell'app. Prima ogni campo era un riquadro dentro il
riquadro, con l'etichetta che saltava sopra il testo al primo tocco:
un gesto da modulo web, non da applicazione. Qui l'etichetta sta
ferma sopra il campo e non si muove mai. *@
<div class="onboarding__fields">
<label class="onboarding__field">
<span class="onboarding__label">Username</span>
<input class="onboarding__input" type="text" autocomplete="username"
autocapitalize="none" autocorrect="off" enterkeyhint="next"
value="@UserData.Username" @oninput="@(e => UserData.Username = e.Value?.ToString())"/>
</label>
<label class="onboarding__field">
<span class="onboarding__label">Password</span>
<span class="onboarding__input-row">
<input class="onboarding__input" type="@(_isShow ? "text" : "password")"
autocomplete="current-password" enterkeyhint="next"
value="@UserData.Password" @oninput="@(e => UserData.Password = e.Value?.ToString())"/>
<button type="button" class="onboarding__reveal" @onclick="ShowPassword"
aria-label="@(_isShow ? "Nascondi la password" : "Mostra la password")">
<i class="@(_isShow ? "ri-eye-off-line" : "ri-eye-line")" aria-hidden="true"></i>
</button>
</span>
</label>
<label class="onboarding__field">
<span class="onboarding__label">Profilo azienda</span>
<input class="onboarding__input" type="text" autocomplete="organization"
autocapitalize="none" autocorrect="off" enterkeyhint="go"
value="@UserData.CodHash" @oninput="@(e => UserData.CodHash = e.Value?.ToString())"/>
</label>
</div>
@if (_attemptFailed)
{
@* Stesso riquadro di avviso usato dentro l'app: l'errore di accesso
non e' un caso speciale che merita un suo stile. *@
<div class="feedback feedback--danger onboarding__error" role="alert" aria-live="assertive">
<i class="feedback__icon ri-error-warning-line" aria-hidden="true"></i>
<span>@ErrorMessage</span>
</div>
}
<button type="submit" class="onboarding__submit" disabled="@(_busy || !CanSubmit)">
@if (_busy)
{
<span class="onboarding__spinner" aria-hidden="true"></span>
<span>Accesso in corso…</span>
}
else
{
<span>Accedi</span>
}
</button>
<div class="onboarding__footer">
<span>@GenericSystemService.GetCurrentAppVersion() · Powered by</span>
<img src="_content/SteUp.Shared/images/logoIntegry.svg" alt="Integry"/>
</div>
</form>
</div>
@code {
private SignIn UserData { get; } = new();
private string ErrorMessage { get; set; } = "";
private bool _attemptFailed;
private bool _busy;
private bool _isShow;
private bool CanSubmit =>
!string.IsNullOrWhiteSpace(UserData.Username) &&
!string.IsNullOrWhiteSpace(UserData.Password) &&
!string.IsNullOrWhiteSpace(UserData.CodHash);
private void ShowPassword() => _isShow = !_isShow;
protected override void OnInitialized()
{
UserData.CodHash = LocalStorage.GetString("codHash");
StateHasChanged();
}
private async Task SignInUser()
{
if (_busy || !CanSubmit) return;
_attemptFailed = false;
_busy = true;
StateHasChanged();
try
{
SteupDataService.RegisterAppVersion();
await UserAccountService.Login(UserData.Username!, UserData.Password!, UserData.CodHash!);
AuthenticationStateProvider.NotifyAuthenticationState(); //Chiamato per forzare il refresh
await SteupDataService.Init();
BarcodeManager.Init();
LocalStorage.SetString("codHash", UserData.CodHash!);
NavigationManager.NavigateTo("/");
}
catch (Exception e)
{
ErrorMessage = e.Message;
Logger.LogError(e, ErrorMessage);
_attemptFailed = true;
}
finally
{
_busy = false;
StateHasChanged();
}
}
public class SignIn
{
public string? Username { get; set; }
public string? Password { get; set; }
public string? CodHash { get; set; }
}
}