import 'package:flutter/material.dart'; import 'package:google_fonts/google_fonts.dart'; import '../config/display_config.dart'; import 'custom_app_text_field.dart'; /// Widget générique pour afficher un champ de formulaire /// S'adapte automatiquement selon le DisplayConfig (editable/readonly, mobile/desktop) class FormFieldWrapper extends StatelessWidget { /// Configuration d'affichage final DisplayConfig config; /// Label du champ final String label; /// Valeur actuelle final String value; /// Controller pour le mode éditable final TextEditingController? controller; /// Callback de changement (mode éditable) final ValueChanged? onChanged; /// Hint du champ (mode éditable) final String? hint; /// Nombre de lignes (pour textarea) final int? maxLines; /// Type de clavier final TextInputType? keyboardType; /// Widget personnalisé à afficher (override le champ standard) final Widget? customWidget; const FormFieldWrapper({ super.key, required this.config, required this.label, required this.value, this.controller, this.onChanged, this.hint, this.maxLines, this.keyboardType, this.customWidget, }); @override Widget build(BuildContext context) { if (config.isReadonly) { return _buildReadonlyField(context); } else { return _buildEditableField(context); } } /// Construit un champ en mode lecture seule Widget _buildReadonlyField(BuildContext context) { return Padding( padding: EdgeInsets.symmetric( vertical: LayoutHelper.getSpacing(context, mobileSpacing: 8.0, desktopSpacing: 12.0, ), ), child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ // Label Text( label, style: GoogleFonts.merienda( fontSize: config.isMobile ? 14 : 16, fontWeight: FontWeight.bold, color: const Color(0xFF4A4A4A), ), ), const SizedBox(height: 6), // Valeur avec fond beige Container( width: double.infinity, padding: const EdgeInsets.symmetric( horizontal: 16, vertical: 12, ), decoration: BoxDecoration( image: const DecorationImage( image: AssetImage('assets/images/bg_beige.png'), fit: BoxFit.fill, ), borderRadius: BorderRadius.circular(8), ), child: Text( value.isEmpty ? '-' : value, style: GoogleFonts.merienda( fontSize: config.isMobile ? 14 : 16, color: const Color(0xFF2C2C2C), ), ), ), ], ), ); } /// Construit un champ en mode éditable Widget _buildEditableField(BuildContext context) { // Si un widget personnalisé est fourni, l'utiliser if (customWidget != null) { return Padding( padding: EdgeInsets.symmetric( vertical: LayoutHelper.getSpacing(context, mobileSpacing: 8.0, desktopSpacing: 12.0, ), ), child: customWidget, ); } // Sinon, utiliser le champ standard return Padding( padding: EdgeInsets.symmetric( vertical: LayoutHelper.getSpacing(context, mobileSpacing: 8.0, desktopSpacing: 12.0, ), ), child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ // Label Text( label, style: GoogleFonts.merienda( fontSize: config.isMobile ? 14 : 16, fontWeight: FontWeight.w600, color: const Color(0xFF4A4A4A), ), ), const SizedBox(height: 8), // Champ de saisie CustomAppTextField( controller: controller!, labelText: label, hintText: hint ?? label, keyboardType: keyboardType ?? TextInputType.text, fieldWidth: double.infinity, ), ], ), ); } } /// Widget générique pour afficher une ligne de champs /// S'adapte automatiquement: horizontal sur desktop, vertical sur mobile class FormFieldRow extends StatelessWidget { /// Configuration d'affichage final DisplayConfig config; /// Liste des champs à afficher final List fields; /// Espacement entre les champs final double? spacing; const FormFieldRow({ super.key, required this.config, required this.fields, this.spacing, }); @override Widget build(BuildContext context) { final effectiveSpacing = spacing ?? LayoutHelper.getSpacing(context, mobileSpacing: 12.0, desktopSpacing: 20.0, ); if (config.isMobile) { // Layout vertical sur mobile return Column( crossAxisAlignment: CrossAxisAlignment.start, children: fields, ); } else { // Layout horizontal sur desktop return Row( crossAxisAlignment: CrossAxisAlignment.start, children: [ for (int i = 0; i < fields.length; i++) ...[ Expanded(child: fields[i]), if (i < fields.length - 1) SizedBox(width: effectiveSpacing), ], ], ); } } }