|
|
|
@ -1939,13 +1939,16 @@ void _showPointVenteDetails(Map<String, dynamic> pointVenteData) async { |
|
|
|
), |
|
|
|
); |
|
|
|
} |
|
|
|
Widget _buildCommandeCardForDialog( |
|
|
|
Commande commande, |
|
|
|
Set<int> expandedCommandes, |
|
|
|
StateSetter setDialogState, |
|
|
|
) { |
|
|
|
final int commandeId = commande.id ?? -1; // fallback si null |
|
|
|
final bool isExpanded = expandedCommandes.contains(commandeId); |
|
|
|
|
|
|
|
// NOUVELLE VERSION de _buildCommandeCardForDialog qui utilise les paramètres du dialog |
|
|
|
Widget _buildCommandeCardForDialog(Commande commande, Set<int> expandedCommandes, StateSetter setDialogState) { |
|
|
|
final bool isExpanded = expandedCommandes.contains(commande.id); |
|
|
|
|
|
|
|
return FutureBuilder<List<DetailCommande>>( |
|
|
|
future: _database.getDetailsCommande(commande.id!), |
|
|
|
future: _database.getDetailsCommande(commandeId), |
|
|
|
builder: (context, snapshot) { |
|
|
|
double totalRemises = 0; |
|
|
|
bool aDesRemises = false; |
|
|
|
@ -1958,45 +1961,37 @@ Widget _buildCommandeCardForDialog(Commande commande, Set<int> expandedCommandes |
|
|
|
} |
|
|
|
|
|
|
|
return AnimatedContainer( |
|
|
|
duration: Duration(milliseconds: 300), |
|
|
|
duration: const Duration(milliseconds: 300), |
|
|
|
curve: Curves.easeInOut, |
|
|
|
margin: EdgeInsets.symmetric(vertical: 4), |
|
|
|
margin: const EdgeInsets.symmetric(vertical: 4), |
|
|
|
child: Material( |
|
|
|
elevation: isExpanded ? 4 : 2, |
|
|
|
borderRadius: BorderRadius.circular(8), |
|
|
|
child: Container( |
|
|
|
child: Container( |
|
|
|
decoration: BoxDecoration( |
|
|
|
color: isExpanded |
|
|
|
? Colors.grey.shade100 |
|
|
|
: Colors.grey.shade200, |
|
|
|
color: isExpanded ? Colors.grey.shade100 : Colors.grey.shade200, |
|
|
|
borderRadius: BorderRadius.circular(8), |
|
|
|
border: aDesRemises |
|
|
|
border: aDesRemises |
|
|
|
? Border.all(color: Colors.orange.shade300, width: 1) |
|
|
|
: null, |
|
|
|
), |
|
|
|
|
|
|
|
child: InkWell( |
|
|
|
onTap: () { |
|
|
|
print('Card tapped! Current state: $isExpanded'); |
|
|
|
// UTILISER setDialogState au lieu de setState |
|
|
|
setDialogState(() { |
|
|
|
if (isExpanded) { |
|
|
|
expandedCommandes.remove(commande.id); |
|
|
|
print('Removed commande ${commande.id}'); |
|
|
|
expandedCommandes.remove(commandeId); |
|
|
|
} else { |
|
|
|
expandedCommandes.add(commande.id!); |
|
|
|
print('Added commande ${commande.id}'); |
|
|
|
expandedCommandes.add(commandeId); |
|
|
|
} |
|
|
|
print('Current expanded: $expandedCommandes'); |
|
|
|
}); |
|
|
|
}, |
|
|
|
borderRadius: BorderRadius.circular(8), |
|
|
|
child: Padding( |
|
|
|
padding: EdgeInsets.all(12), |
|
|
|
padding: const EdgeInsets.all(12), |
|
|
|
child: Column( |
|
|
|
crossAxisAlignment: CrossAxisAlignment.start, |
|
|
|
children: [ |
|
|
|
// En-tête de la commande (toujours visible) |
|
|
|
// En-tête |
|
|
|
Row( |
|
|
|
children: [ |
|
|
|
Container( |
|
|
|
@ -2006,7 +2001,7 @@ Widget _buildCommandeCardForDialog(Commande commande, Set<int> expandedCommandes |
|
|
|
color: _getStatutColor(commande.statut).withOpacity(0.1), |
|
|
|
borderRadius: BorderRadius.circular(20), |
|
|
|
border: aDesRemises |
|
|
|
? Border.all(color: Colors.orange.shade300, width: 1) |
|
|
|
? Border.all(color: Colors.orange.shade300) |
|
|
|
: null, |
|
|
|
), |
|
|
|
child: Column( |
|
|
|
@ -2024,8 +2019,8 @@ Widget _buildCommandeCardForDialog(Commande commande, Set<int> expandedCommandes |
|
|
|
: Colors.blue.shade600, |
|
|
|
), |
|
|
|
Text( |
|
|
|
'#${commande.id}', |
|
|
|
style: TextStyle( |
|
|
|
'#$commandeId', |
|
|
|
style: const TextStyle( |
|
|
|
fontSize: 8, |
|
|
|
fontWeight: FontWeight.bold, |
|
|
|
), |
|
|
|
@ -2033,31 +2028,32 @@ Widget _buildCommandeCardForDialog(Commande commande, Set<int> expandedCommandes |
|
|
|
], |
|
|
|
), |
|
|
|
), |
|
|
|
SizedBox(width: 12), |
|
|
|
const SizedBox(width: 12), |
|
|
|
Expanded( |
|
|
|
child: Column( |
|
|
|
crossAxisAlignment: CrossAxisAlignment.start, |
|
|
|
children: [ |
|
|
|
Text( |
|
|
|
commande.clientNomComplet, |
|
|
|
style: TextStyle( |
|
|
|
style: const TextStyle( |
|
|
|
fontSize: 14, |
|
|
|
fontWeight: FontWeight.bold, |
|
|
|
), |
|
|
|
overflow: TextOverflow.ellipsis, |
|
|
|
), |
|
|
|
SizedBox(height: 2), |
|
|
|
const SizedBox(height: 2), |
|
|
|
Row( |
|
|
|
children: [ |
|
|
|
Icon(Icons.calendar_today, size: 12, color: Colors.grey), |
|
|
|
SizedBox(width: 4), |
|
|
|
const Icon(Icons.calendar_today, |
|
|
|
size: 12, color: Colors.grey), |
|
|
|
const SizedBox(width: 4), |
|
|
|
Text( |
|
|
|
DateFormat('dd/MM/yyyy').format(commande.dateCommande), |
|
|
|
style: TextStyle(fontSize: 11, color: Colors.grey), |
|
|
|
style: const TextStyle(fontSize: 11, color: Colors.grey), |
|
|
|
), |
|
|
|
SizedBox(width: 12), |
|
|
|
const SizedBox(width: 12), |
|
|
|
Container( |
|
|
|
padding: EdgeInsets.symmetric(horizontal: 6, vertical: 2), |
|
|
|
padding: const EdgeInsets.symmetric(horizontal: 6, vertical: 2), |
|
|
|
decoration: BoxDecoration( |
|
|
|
color: _getStatutColor(commande.statut).withOpacity(0.2), |
|
|
|
borderRadius: BorderRadius.circular(10), |
|
|
|
@ -2078,10 +2074,9 @@ Widget _buildCommandeCardForDialog(Commande commande, Set<int> expandedCommandes |
|
|
|
], |
|
|
|
), |
|
|
|
), |
|
|
|
// Icône d'expansion |
|
|
|
AnimatedRotation( |
|
|
|
turns: isExpanded ? 0.5 : 0, |
|
|
|
duration: Duration(milliseconds: 300), |
|
|
|
duration: const Duration(milliseconds: 300), |
|
|
|
child: Icon( |
|
|
|
Icons.expand_more, |
|
|
|
color: Colors.grey[600], |
|
|
|
@ -2089,14 +2084,13 @@ Widget _buildCommandeCardForDialog(Commande commande, Set<int> expandedCommandes |
|
|
|
), |
|
|
|
], |
|
|
|
), |
|
|
|
|
|
|
|
SizedBox(height: 8), |
|
|
|
|
|
|
|
// Montant (toujours visible) |
|
|
|
const SizedBox(height: 8), |
|
|
|
// Montant |
|
|
|
Row( |
|
|
|
children: [ |
|
|
|
Icon(Icons.attach_money, size: 14, color: Colors.green.shade600), |
|
|
|
SizedBox(width: 4), |
|
|
|
Icon(Icons.attach_money, |
|
|
|
size: 14, color: Colors.green.shade600), |
|
|
|
const SizedBox(width: 4), |
|
|
|
Text( |
|
|
|
'${NumberFormat('#,##0', 'fr_FR').format(commande.montantTotal)} MGA', |
|
|
|
style: TextStyle( |
|
|
|
@ -2106,9 +2100,9 @@ Widget _buildCommandeCardForDialog(Commande commande, Set<int> expandedCommandes |
|
|
|
), |
|
|
|
), |
|
|
|
if (totalRemises > 0) ...[ |
|
|
|
SizedBox(width: 8), |
|
|
|
const SizedBox(width: 8), |
|
|
|
Container( |
|
|
|
padding: EdgeInsets.symmetric(horizontal: 4, vertical: 2), |
|
|
|
padding: const EdgeInsets.symmetric(horizontal: 4, vertical: 2), |
|
|
|
decoration: BoxDecoration( |
|
|
|
color: Colors.orange.shade100, |
|
|
|
borderRadius: BorderRadius.circular(8), |
|
|
|
@ -2116,176 +2110,103 @@ Widget _buildCommandeCardForDialog(Commande commande, Set<int> expandedCommandes |
|
|
|
child: Row( |
|
|
|
mainAxisSize: MainAxisSize.min, |
|
|
|
children: [ |
|
|
|
Icon(Icons.discount, size: 10, color: Colors.teal.shade700), |
|
|
|
SizedBox(width: 2), |
|
|
|
Icon(Icons.discount, |
|
|
|
size: 10, color: Colors.teal.shade700), |
|
|
|
const SizedBox(width: 2), |
|
|
|
Text( |
|
|
|
'-${NumberFormat('#,##0', 'fr_FR').format(totalRemises)}', |
|
|
|
style: TextStyle( |
|
|
|
style: const TextStyle( |
|
|
|
fontSize: 9, |
|
|
|
fontWeight: FontWeight.bold, |
|
|
|
color: Colors.teal.shade700, |
|
|
|
), |
|
|
|
), |
|
|
|
], |
|
|
|
), |
|
|
|
), |
|
|
|
], |
|
|
|
] |
|
|
|
], |
|
|
|
), |
|
|
|
|
|
|
|
// Détails étendus avec AnimatedSize |
|
|
|
// Contenu étendu |
|
|
|
AnimatedSize( |
|
|
|
duration: Duration(milliseconds: 300), |
|
|
|
duration: const Duration(milliseconds: 300), |
|
|
|
curve: Curves.easeInOut, |
|
|
|
child: isExpanded ? Column( |
|
|
|
crossAxisAlignment: CrossAxisAlignment.start, |
|
|
|
children: [ |
|
|
|
SizedBox(height: 12), |
|
|
|
Divider(color: Colors.grey[300]), |
|
|
|
SizedBox(height: 8), |
|
|
|
|
|
|
|
// Informations du commandeur |
|
|
|
if (commande.commandeurnom != null && commande.commandeurnom!.isNotEmpty) |
|
|
|
Container( |
|
|
|
padding: EdgeInsets.all(8), |
|
|
|
decoration: BoxDecoration( |
|
|
|
color: Colors.blue.shade50, |
|
|
|
borderRadius: BorderRadius.circular(6), |
|
|
|
), |
|
|
|
child: Row( |
|
|
|
children: [ |
|
|
|
Icon(Icons.person, size: 16, color: Colors.blue[600]), |
|
|
|
SizedBox(width: 8), |
|
|
|
Text( |
|
|
|
'Commandeur: ', |
|
|
|
style: TextStyle( |
|
|
|
fontSize: 12, |
|
|
|
fontWeight: FontWeight.w500, |
|
|
|
color: Colors.grey[700], |
|
|
|
), |
|
|
|
), |
|
|
|
Expanded( |
|
|
|
child: Text( |
|
|
|
'${commande.commandeurnom ?? ''} ${commande.commandeurPrenom ?? ''}', |
|
|
|
style: TextStyle( |
|
|
|
fontSize: 12, |
|
|
|
fontWeight: FontWeight.bold, |
|
|
|
color: Colors.blue[700], |
|
|
|
), |
|
|
|
), |
|
|
|
), |
|
|
|
], |
|
|
|
), |
|
|
|
), |
|
|
|
|
|
|
|
SizedBox(height: 8), |
|
|
|
|
|
|
|
// Statut détaillé |
|
|
|
Container( |
|
|
|
padding: EdgeInsets.all(8), |
|
|
|
decoration: BoxDecoration( |
|
|
|
color: _getStatutColor(commande.statut).withOpacity(0.1), |
|
|
|
borderRadius: BorderRadius.circular(6), |
|
|
|
), |
|
|
|
child: Row( |
|
|
|
child: isExpanded |
|
|
|
? Column( |
|
|
|
children: [ |
|
|
|
Icon( |
|
|
|
_getStatutIcon(commande.statut), |
|
|
|
size: 16, |
|
|
|
color: commande.statut == StatutCommande.annulee |
|
|
|
? Colors.red |
|
|
|
: Colors.blue[600], |
|
|
|
), |
|
|
|
SizedBox(width: 8), |
|
|
|
Text( |
|
|
|
'Statut: ', |
|
|
|
style: TextStyle( |
|
|
|
fontSize: 12, |
|
|
|
fontWeight: FontWeight.w500, |
|
|
|
color: Colors.grey[700], |
|
|
|
), |
|
|
|
), |
|
|
|
Text( |
|
|
|
commande.statutLibelle, |
|
|
|
style: TextStyle( |
|
|
|
fontSize: 12, |
|
|
|
fontWeight: FontWeight.bold, |
|
|
|
color: commande.statut == StatutCommande.annulee |
|
|
|
? Colors.red |
|
|
|
: Colors.blue[700], |
|
|
|
), |
|
|
|
), |
|
|
|
], |
|
|
|
), |
|
|
|
), |
|
|
|
|
|
|
|
SizedBox(height: 8), |
|
|
|
|
|
|
|
// Liste des produits commandés |
|
|
|
if (snapshot.hasData && snapshot.data!.isNotEmpty) ...[ |
|
|
|
Container( |
|
|
|
padding: EdgeInsets.all(8), |
|
|
|
decoration: BoxDecoration( |
|
|
|
color: Colors.green.shade50, |
|
|
|
borderRadius: BorderRadius.circular(6), |
|
|
|
), |
|
|
|
child: Column( |
|
|
|
crossAxisAlignment: CrossAxisAlignment.start, |
|
|
|
children: [ |
|
|
|
Row( |
|
|
|
children: [ |
|
|
|
Icon(Icons.shopping_cart, size: 16, color: Colors.green[600]), |
|
|
|
SizedBox(width: 8), |
|
|
|
Text( |
|
|
|
'Produits commandés:', |
|
|
|
style: TextStyle( |
|
|
|
fontSize: 12, |
|
|
|
fontWeight: FontWeight.bold, |
|
|
|
color: Colors.green[700], |
|
|
|
), |
|
|
|
), |
|
|
|
], |
|
|
|
), |
|
|
|
SizedBox(height: 6), |
|
|
|
...snapshot.data!.map((detail) => Padding( |
|
|
|
padding: EdgeInsets.only(left: 24, bottom: 4), |
|
|
|
const SizedBox(height: 12), |
|
|
|
Divider(color: Colors.grey[300]), |
|
|
|
if (commande.commandeurnom?.isNotEmpty ?? false) |
|
|
|
Padding( |
|
|
|
padding: const EdgeInsets.only(top: 8.0), |
|
|
|
child: Row( |
|
|
|
children: [ |
|
|
|
Container( |
|
|
|
width: 4, |
|
|
|
height: 4, |
|
|
|
decoration: BoxDecoration( |
|
|
|
color: Colors.green[600], |
|
|
|
borderRadius: BorderRadius.circular(2), |
|
|
|
), |
|
|
|
), |
|
|
|
SizedBox(width: 8), |
|
|
|
Expanded( |
|
|
|
child: Text( |
|
|
|
'${detail.produitNom} (x${detail.quantite})', |
|
|
|
style: TextStyle( |
|
|
|
fontSize: 11, |
|
|
|
color: Colors.green[700], |
|
|
|
), |
|
|
|
), |
|
|
|
), |
|
|
|
Icon(Icons.person, |
|
|
|
size: 16, color: Colors.blue[600]), |
|
|
|
const SizedBox(width: 8), |
|
|
|
Text( |
|
|
|
'${NumberFormat('#,##0', 'fr_FR').format(detail.sousTotal)} MGA', |
|
|
|
'${commande.commandeurnom ?? ''} ${commande.commandeurPrenom ?? ''}', |
|
|
|
style: TextStyle( |
|
|
|
fontSize: 11, |
|
|
|
fontWeight: FontWeight.w500, |
|
|
|
color: Colors.green[700], |
|
|
|
fontSize: 12, |
|
|
|
fontWeight: FontWeight.bold, |
|
|
|
color: Colors.blue[700], |
|
|
|
), |
|
|
|
), |
|
|
|
], |
|
|
|
), |
|
|
|
)).toList(), |
|
|
|
], |
|
|
|
), |
|
|
|
), |
|
|
|
], |
|
|
|
], |
|
|
|
) : SizedBox.shrink(), |
|
|
|
), |
|
|
|
const SizedBox(height: 8), |
|
|
|
if (snapshot.hasData && snapshot.data!.isNotEmpty) |
|
|
|
Column( |
|
|
|
crossAxisAlignment: CrossAxisAlignment.start, |
|
|
|
children: [ |
|
|
|
Row( |
|
|
|
children: [ |
|
|
|
Icon(Icons.shopping_cart, |
|
|
|
size: 16, color: Colors.green[600]), |
|
|
|
const SizedBox(width: 8), |
|
|
|
Text( |
|
|
|
'Produits commandés:', |
|
|
|
style: TextStyle( |
|
|
|
fontSize: 12, |
|
|
|
fontWeight: FontWeight.bold, |
|
|
|
color: Colors.green[700], |
|
|
|
), |
|
|
|
), |
|
|
|
], |
|
|
|
), |
|
|
|
const SizedBox(height: 6), |
|
|
|
...snapshot.data!.map((detail) => Padding( |
|
|
|
padding: const EdgeInsets.only(left: 24, bottom: 4), |
|
|
|
child: Row( |
|
|
|
children: [ |
|
|
|
const Icon(Icons.circle, |
|
|
|
size: 4, color: Colors.green), |
|
|
|
const SizedBox(width: 8), |
|
|
|
Expanded( |
|
|
|
child: Text( |
|
|
|
'${detail.produitNom} (x${detail.quantite})', |
|
|
|
style: TextStyle( |
|
|
|
fontSize: 11, |
|
|
|
color: Colors.green[700], |
|
|
|
), |
|
|
|
), |
|
|
|
), |
|
|
|
Text( |
|
|
|
'${NumberFormat('#,##0', 'fr_FR').format(detail.sousTotal)} MGA', |
|
|
|
style: TextStyle( |
|
|
|
fontSize: 11, |
|
|
|
fontWeight: FontWeight.w500, |
|
|
|
color: Colors.green[700], |
|
|
|
), |
|
|
|
), |
|
|
|
], |
|
|
|
), |
|
|
|
)) |
|
|
|
], |
|
|
|
), |
|
|
|
], |
|
|
|
) |
|
|
|
: const SizedBox.shrink(), |
|
|
|
), |
|
|
|
], |
|
|
|
), |
|
|
|
@ -2297,6 +2218,7 @@ Widget _buildCommandeCardForDialog(Commande commande, Set<int> expandedCommandes |
|
|
|
}, |
|
|
|
); |
|
|
|
} |
|
|
|
|
|
|
|
Color _getStatutColor(StatutCommande statut) { |
|
|
|
switch (statut) { |
|
|
|
case StatutCommande.enAttente: |
|
|
|
|