This commit is contained in:
2026-08-07 14:34:25 +05:30
parent 829e5a8188
commit 0988d39d8b
19 changed files with 850 additions and 932 deletions

View File

@@ -1,3 +1,5 @@
import 'dart:ui';
import 'package:flutter/material.dart';
import 'package:flutter_animate/flutter_animate.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';
@@ -7,7 +9,7 @@ import '../../../app/providers.dart';
import '../../../core/router/app_router.dart';
import '../../../core/theme/app_colors.dart';
import '../../../core/theme/app_dimens.dart';
import '../../../core/utils/validators.dart';
import '../../../core/widgets/brand_mark.dart';
import '../../../core/widgets/primary_button.dart';
import '../providers/auth_controller.dart';
@@ -29,9 +31,11 @@ class LoginScreen extends ConsumerStatefulWidget {
class _LoginScreenState extends ConsumerState<LoginScreen> {
final _formKey = GlobalKey<FormState>();
// Both fields start empty. There is nothing to prefill: a person signs in
// with their own back-office account, and which shell they get is a property
// of that account rather than a tab they picked before typing.
// Blank on purpose. The role tabs that used to sit above these fields chose
// between two built-in accounts and decided, locally, whether the terminal
// opened the admin shell or the billing screen. The back office decides that
// now — `POST /login` answers with the role — so offering the choice here
// would only let someone pick a screen the server is about to override.
final _email = TextEditingController();
final _password = TextEditingController();
@@ -247,15 +251,17 @@ class _Card extends StatelessWidget {
),
const SizedBox(height: AppSpacing.xl),
const _Label('Store email'),
const _Label('Email or username'),
TextFormField(
controller: email,
keyboardType: TextInputType.emailAddress,
textInputAction: TextInputAction.next,
enabled: !busy,
validator: (v) => (v ?? '').trim().isEmpty
? 'Store email is required'
: Validators.emailOptional(v),
// Not validated as an email. The back office takes this as
// `authname` and accepts either form; rejecting a username here
// would block an account the server would have let in.
validator: (v) =>
(v ?? '').trim().isEmpty ? 'This is required' : null,
decoration: const InputDecoration(
hintText: 'store@example.in',
prefixIcon: Icon(Icons.storefront_outlined),
@@ -270,9 +276,8 @@ class _Card extends StatelessWidget {
enabled: !busy,
textInputAction: TextInputAction.done,
onFieldSubmitted: (_) => onSubmit(),
validator: (v) => (v ?? '').isEmpty
? 'Password is required'
: ((v ?? '').length < 6 ? 'Password looks too short' : null),
validator: (v) =>
(v ?? '').isEmpty ? 'Password is required' : null,
decoration: InputDecoration(
hintText: 'Enter your password',
prefixIcon: const Icon(Icons.lock_outline_rounded),
@@ -393,3 +398,4 @@ class _Label extends StatelessWidget {
);
}
}