Test validation lancement lavage

This commit is contained in:
bastien
2026-07-09 23:08:28 +02:00
parent eb4c322001
commit cef740de26
2 changed files with 198 additions and 1 deletions
@@ -0,0 +1,160 @@
import 'package:flutter/material.dart';
import 'package:go_router/go_router.dart';
import 'package:intl/intl.dart';
import '../router/app_router.dart';
import '../theme/app_colors.dart';
/// Fenêtre de confirmation avant le lancement d'un lavage.
class WashStartConfirmationDialog {
static Future<bool> show(
BuildContext context, {
required String machineName,
required double currentBalance,
required double price,
required NumberFormat currency,
}) async {
final remainingBalance = currentBalance - price;
final hasEnoughBalance = remainingBalance >= 0;
final result = await showDialog<bool>(
context: context,
builder: (dialogContext) => AlertDialog(
shape: RoundedRectangleBorder(borderRadius: BorderRadius.circular(16)),
title: const Text('Confirmer le lavage'),
content: Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.stretch,
children: [
Text(
machineName,
style: Theme.of(dialogContext).textTheme.bodyMedium?.copyWith(
color: AppColors.textSecondary,
),
),
const SizedBox(height: 16),
Container(
padding: const EdgeInsets.all(16),
decoration: BoxDecoration(
color: AppColors.background,
borderRadius: BorderRadius.circular(12),
border: Border.all(color: AppColors.divider),
),
child: Column(
children: [
_AmountRow(
label: 'Solde actuel',
amount: currency.format(currentBalance),
emphasized: true,
),
const SizedBox(height: 12),
_AmountRow(
label: 'Prix du cycle',
amount: ' ${currency.format(price)}',
color: AppColors.textSecondary,
),
const Padding(
padding: EdgeInsets.symmetric(vertical: 12),
child: Divider(height: 1),
),
_AmountRow(
label: 'Solde restant',
amount: currency.format(remainingBalance),
emphasized: true,
color: hasEnoughBalance ? AppColors.success : AppColors.error,
),
],
),
),
if (!hasEnoughBalance) ...[
const SizedBox(height: 12),
Container(
padding: const EdgeInsets.all(12),
decoration: BoxDecoration(
color: AppColors.error.withValues(alpha: 0.08),
borderRadius: BorderRadius.circular(10),
),
child: Row(
children: [
const Icon(Icons.warning_amber_rounded, color: AppColors.error, size: 20),
const SizedBox(width: 8),
Expanded(
child: Text(
'Solde insuffisant. Rechargez votre portefeuille pour continuer.',
style: Theme.of(dialogContext).textTheme.bodySmall?.copyWith(
color: AppColors.error,
fontWeight: FontWeight.w500,
),
),
),
],
),
),
],
],
),
actions: [
TextButton(
onPressed: () => Navigator.pop(dialogContext, false),
child: const Text('Annuler'),
),
if (!hasEnoughBalance)
TextButton(
onPressed: () {
Navigator.pop(dialogContext, false);
dialogContext.push(AppRoutes.walletTopUp);
},
child: const Text('Recharger'),
)
else
ElevatedButton(
onPressed: () => Navigator.pop(dialogContext, true),
child: const Text('Démarrer le lavage'),
),
],
),
);
return result ?? false;
}
}
class _AmountRow extends StatelessWidget {
const _AmountRow({
required this.label,
required this.amount,
this.emphasized = false,
this.color,
});
final String label;
final String amount;
final bool emphasized;
final Color? color;
@override
Widget build(BuildContext context) {
final amountColor = color ?? AppColors.textPrimary;
return Row(
children: [
Expanded(
child: Text(
label,
style: Theme.of(context).textTheme.bodyMedium?.copyWith(
fontWeight: emphasized ? FontWeight.w600 : FontWeight.normal,
),
),
),
Text(
amount,
style: Theme.of(context).textTheme.titleMedium?.copyWith(
color: amountColor,
fontWeight: emphasized ? FontWeight.w700 : FontWeight.w600,
fontSize: emphasized ? 18 : 16,
),
),
],
);
}
}