import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:em2rp/models/vehicle_model.dart';
import 'package:em2rp/models/depot_model.dart';
import 'package:em2rp/models/route_result_model.dart';
import 'package:em2rp/services/vehicle_service.dart';
import 'package:em2rp/services/travel_service.dart';
import 'package:em2rp/utils/colors.dart';
import 'package:em2rp/views/widgets/common/route_map_widget.dart';

/// Dialog complète de calcul des frais de déplacement.
/// Retourne le prix calculé si l'utilisateur sélectionne un itinéraire,
/// null sinon.
Future<double?> showTravelCostDialog({
  required BuildContext context,
  required String eventAddress,
}) {
  return showDialog<double>(
    context: context,
    barrierDismissible: false,
    builder: (ctx) => TravelCostDialog(eventAddress: eventAddress),
  );
}

class TravelCostDialog extends StatefulWidget {
  final String eventAddress;

  const TravelCostDialog({super.key, required this.eventAddress});

  @override
  State<TravelCostDialog> createState() => _TravelCostDialogState();
}

class _TravelCostDialogState extends State<TravelCostDialog> {
  final _vehicleService = VehicleService();
  final _travelService = TravelService();

  // Données chargées
  List<VehicleModel> _vehicles = [];
  List<DepotModel> _depots = [];
  FuelPrices _fuelPrices = const FuelPrices();

  // Sélections
  VehicleModel? _selectedVehicle;
  DepotModel? _selectedDepot;
  int _nbTechnicians = 2;
  double _hourlyRate = 25.0;
  bool _applyFreeZone = false;
  double _freeZoneKm = 20.0;
  int _freeZoneMinutes = 20;

  // Résultats
  List<RouteResult> _routes = [];
  RouteResult? _selectedRoute;

  // État
  bool _isLoadingData = true;
  bool _isCalculating = false;
  String? _error;

  final _hourlyCtrl = TextEditingController(text: '25');

  @override
  void initState() {
    super.initState();
    _loadData();
  }

  @override
  void dispose() {
    _hourlyCtrl.dispose();
    super.dispose();
  }

  Future<void> _loadData() async {
    setState(() => _isLoadingData = true);
    try {
      final results = await Future.wait([
        _vehicleService.getVehicles(),
        _travelService.getDepots(),
        _travelService.getFuelPrices(),
      ]);
      final vehicles = results[0] as List<VehicleModel>;
      final depots = results[1] as List<DepotModel>;
      final prices = results[2] as FuelPrices;

      if (mounted) {
        setState(() {
          _vehicles = vehicles;
          _depots = depots;
          _fuelPrices = prices;
          _selectedVehicle = vehicles.isNotEmpty ? vehicles.first : null;
          _selectedDepot = depots.isNotEmpty ? depots.first : null;
          _isLoadingData = false;
        });
      }
    } catch (e) {
      if (mounted) {
        setState(() {
          _error = 'Erreur lors du chargement: $e';
          _isLoadingData = false;
        });
      }
    }
  }

  Future<void> _calculate() async {
    if (_selectedVehicle == null || _selectedDepot == null) return;

    setState(() {
      _isCalculating = true;
      _error = null;
      _routes = [];
      _selectedRoute = null;
    });

    try {
      final routes = await _travelService.computeRoutes(
        origin: _selectedDepot!.address,
        destination: widget.eventAddress,
        vehicleTollCategory: _selectedVehicle!.tollCategoryId,
      );

      if (mounted) {
        setState(() {
          _routes = routes;
          _isCalculating = false;
        });
      }
    } catch (e) {
      if (mounted) {
        setState(() {
          _error = 'Erreur de calcul: $e';
          _isCalculating = false;
        });
      }
    }
  }

  void _selectRoute(RouteResult route) {
    final total = route.totalCost(
      consumptionPer100km: _selectedVehicle!.consumptionPer100km,
      fuelPricePerLiter: _fuelPrices.priceForFuelType(_selectedVehicle!.fuelType),
      maintenanceCostPerKm: _selectedVehicle!.maintenanceCostPerKm,
      nbTechnicians: _nbTechnicians,
      hourlyRate: _hourlyRate,
      freeZoneKm: _applyFreeZone ? _freeZoneKm : 0.0,
      freeZoneMinutes: _applyFreeZone ? _freeZoneMinutes.toDouble() : 0.0,
    );
    Navigator.of(context).pop(total);
  }

  String _formatDuration(int seconds) {
    final h = seconds ~/ 3600;
    final m = (seconds % 3600) ~/ 60;
    if (h == 0) return '${m}min';
    return '${h}h${m.toString().padLeft(2, '0')}';
  }

  String _formatDistance(int meters) {
    final km = meters / 1000.0;
    return '${km.toStringAsFixed(0)} km';
  }

  @override
  Widget build(BuildContext context) {
    final screenW = MediaQuery.of(context).size.width;
    final isWide = screenW > 900;

    return Dialog(
      shape: RoundedRectangleBorder(borderRadius: BorderRadius.circular(16)),
      child: ConstrainedBox(
        constraints: BoxConstraints(
          maxWidth: isWide ? 900 : 600,
          maxHeight: MediaQuery.of(context).size.height * 0.9,
        ),
        child: Column(
          mainAxisSize: MainAxisSize.min,
          children: [
            _buildHeader(),
            Flexible(child: _buildBody()),
          ],
        ),
      ),
    );
  }

  Widget _buildHeader() {
    return Container(
      padding: const EdgeInsets.symmetric(horizontal: 24, vertical: 16),
      decoration: BoxDecoration(
        color: AppColors.rouge,
        borderRadius: const BorderRadius.vertical(top: Radius.circular(16)),
      ),
      child: Row(
        children: [
          const Icon(Icons.route, color: Colors.white, size: 24),
          const SizedBox(width: 12),
          Expanded(
            child: Column(
              crossAxisAlignment: CrossAxisAlignment.start,
              children: [
                const Text(
                  'Calculer les frais de déplacement',
                  style: TextStyle(
                    color: Colors.white,
                    fontSize: 16,
                    fontWeight: FontWeight.bold,
                  ),
                ),
                Text(
                  widget.eventAddress,
                  style: const TextStyle(color: Colors.white70, fontSize: 12),
                  overflow: TextOverflow.ellipsis,
                ),
              ],
            ),
          ),
          IconButton(
            icon: const Icon(Icons.close, color: Colors.white),
            onPressed: () => Navigator.of(context).pop(null),
          ),
        ],
      ),
    );
  }

  Widget _buildBody() {
    if (_isLoadingData) {
      return const Padding(
        padding: EdgeInsets.all(48),
        child: Center(child: CircularProgressIndicator()),
      );
    }

    final screenW = MediaQuery.of(context).size.width;
    final isWide = screenW > 900;

    if (isWide) {
      return Row(
        crossAxisAlignment: CrossAxisAlignment.start,
        children: [
          Expanded(
            flex: 3,
            child: _routes.isEmpty 
              ? const Center(child: Text("Configurez le trajet et cliquez sur Calculer"))
              : RouteMapWidget(routes: _routes, selectedRoute: _selectedRoute),
          ),
          Expanded(
            flex: 2,
            child: SingleChildScrollView(
              padding: const EdgeInsets.all(16),
              child: Column(
                children: [
                  _buildConfigPanel(),
                  if (_routes.isNotEmpty) ...[
                    const Divider(height: 32),
                    _buildResultsPanel(),
                  ]
                ],
              ),
            ),
          ),
        ],
      );
    } else {
      return SingleChildScrollView(
        child: Column(
          children: [
            if (_routes.isNotEmpty)
              SizedBox(
                height: 260,
                child: RouteMapWidget(routes: _routes, selectedRoute: _selectedRoute),
              ),
            Padding(
              padding: const EdgeInsets.all(16),
              child: Column(
                children: [
                  _buildConfigPanel(),
                  if (_routes.isNotEmpty) ...[
                    const Divider(height: 32),
                    _buildResultsPanel(),
                  ]
                ],
              ),
            ),
          ],
        ),
      );
    }
  }

  Widget _buildConfigPanel() {
    return Column(
      crossAxisAlignment: CrossAxisAlignment.start,
      children: [
        if (_error != null)
          Container(
            margin: const EdgeInsets.only(bottom: 16),
            padding: const EdgeInsets.all(12),
            decoration: BoxDecoration(
              color: Colors.red[50],
              borderRadius: BorderRadius.circular(8),
              border: Border.all(color: Colors.red[200]!),
            ),
            child: Row(children: [
              const Icon(Icons.error_outline, color: Colors.red),
              const SizedBox(width: 8),
              Expanded(child: Text(_error!, style: const TextStyle(color: Colors.red))),
            ]),
          ),

        // Dépôt de départ
        _sectionTitle('Dépôt de départ'),
        if (_depots.isEmpty)
          _emptyHint(
              'Aucun dépôt configuré. Ajoutez-en un dans Gestion des données → Dépôts.')
        else
          DropdownButtonFormField<DepotModel>(
            value: _selectedDepot,
            isExpanded: true,
            decoration: const InputDecoration(
              border: OutlineInputBorder(),
              prefixIcon: Icon(Icons.warehouse_outlined),
            ),
            items: _depots
                .map((d) => DropdownMenuItem(
                      value: d,
                      child: Text(
                        '${d.name} — ${d.address}',
                        overflow: TextOverflow.ellipsis,
                      ),
                    ))
                .toList(),
            onChanged: (v) => setState(() => _selectedDepot = v),
          ),

        const SizedBox(height: 20),

        // Véhicule
        _sectionTitle('Véhicule'),
        if (_vehicles.isEmpty)
          _emptyHint(
              'Aucun véhicule configuré. Ajoutez-en un dans Gestion des données → Véhicules.')
        else
          DropdownButtonFormField<VehicleModel>(
            value: _selectedVehicle,
            isExpanded: true,
            decoration: const InputDecoration(
              border: OutlineInputBorder(),
              prefixIcon: Icon(Icons.directions_car_outlined),
            ),
            items: _vehicles
                .map((v) => DropdownMenuItem(
                      value: v,
                      child: Text(
                        '${v.name} — ${v.consumptionPer100km} ${v.consumptionUnit} | Cat. péage ${v.tollCategoryId}',
                        overflow: TextOverflow.ellipsis,
                      ),
                    ))
                .toList(),
            onChanged: (v) => setState(() => _selectedVehicle = v),
          ),

        const SizedBox(height: 20),

        // Techniciens + taux horaire
        _sectionTitle('Main-d\'œuvre'),
        Row(
          children: [
            Expanded(
              child: Column(
                crossAxisAlignment: CrossAxisAlignment.start,
                children: [
                  const Text('Nb techniciens',
                      style: TextStyle(fontSize: 12, color: Colors.grey)),
                  const SizedBox(height: 4),
                  Row(
                    children: [
                      IconButton(
                        icon: const Icon(Icons.remove_circle_outline),
                        onPressed: _nbTechnicians > 1
                            ? () => setState(() => _nbTechnicians--)
                            : null,
                      ),
                      Text(
                        '$_nbTechnicians',
                        style: const TextStyle(
                            fontSize: 20, fontWeight: FontWeight.bold),
                      ),
                      IconButton(
                        icon: const Icon(Icons.add_circle_outline),
                        onPressed: () => setState(() => _nbTechnicians++),
                      ),
                    ],
                  ),
                ],
              ),
            ),
            const SizedBox(width: 16),
            Expanded(
              child: TextFormField(
                controller: _hourlyCtrl,
                decoration: const InputDecoration(
                  labelText: 'Taux horaire',
                  border: OutlineInputBorder(),
                  suffixText: '€/h',
                ),
                keyboardType: const TextInputType.numberWithOptions(decimal: true),
                inputFormatters: [
                  FilteringTextInputFormatter.allow(RegExp(r'^\d+\.?\d{0,2}'))
                ],
                onChanged: (v) {
                  final parsed = double.tryParse(v);
                  if (parsed != null) setState(() => _hourlyRate = parsed);
                },
              ),
            ),
          ],
        ),

        const SizedBox(height: 16),

        // Zone de gratuité
        CheckboxListTile(
          value: _applyFreeZone,
          onChanged: (v) => setState(() => _applyFreeZone = v ?? false),
          activeColor: AppColors.rouge,
          title: const Text('Appliquer la zone de gratuité'),
          subtitle:
              Text('Déduit ${_freeZoneKm.toStringAsFixed(0)} km (carburant + maintenance) et $_freeZoneMinutes min (main-d\'œuvre)'),
          contentPadding: EdgeInsets.zero,
          controlAffinity: ListTileControlAffinity.leading,
        ),
        if (_applyFreeZone)
          Padding(
            padding: const EdgeInsets.only(left: 32, top: 8),
            child: Row(
              children: [
                Expanded(
                  child: TextFormField(
                    initialValue: _freeZoneKm.toStringAsFixed(0),
                    decoration: const InputDecoration(
                      labelText: 'Distance déduite',
                      border: OutlineInputBorder(),
                      suffixText: 'km',
                    ),
                    keyboardType: TextInputType.number,
                    inputFormatters: [
                      FilteringTextInputFormatter.allow(RegExp(r'^\d+\.?\d{0,2}'))
                    ],
                    onChanged: (v) {
                      final parsed = double.tryParse(v);
                      if (parsed != null) setState(() => _freeZoneKm = parsed);
                    },
                  ),
                ),
                const SizedBox(width: 16),
                Expanded(
                  child: TextFormField(
                    initialValue: _freeZoneMinutes.toString(),
                    decoration: const InputDecoration(
                      labelText: 'Temps déduit',
                      border: OutlineInputBorder(),
                      suffixText: 'min',
                    ),
                    keyboardType: TextInputType.number,
                    inputFormatters: [FilteringTextInputFormatter.digitsOnly],
                    onChanged: (v) {
                      final parsed = int.tryParse(v);
                      if (parsed != null) setState(() => _freeZoneMinutes = parsed);
                    },
                  ),
                ),
              ],
            ),
          ),

        const SizedBox(height: 24),

        // Bouton Calculer
        SizedBox(
          width: double.infinity,
          child: ElevatedButton.icon(
            icon: _isCalculating
                ? const SizedBox(
                    width: 18,
                    height: 18,
                    child: CircularProgressIndicator(
                        strokeWidth: 2, color: Colors.white),
                  )
                : const Icon(Icons.calculate_outlined),
            label: Text(_isCalculating ? 'Calcul en cours...' : 'Calculer le trajet'),
            style: ElevatedButton.styleFrom(
              backgroundColor: AppColors.rouge,
              foregroundColor: Colors.white,
              padding: const EdgeInsets.symmetric(vertical: 14),
              textStyle: const TextStyle(fontSize: 16),
            ),
            onPressed: (_isCalculating ||
                    _selectedVehicle == null ||
                    _selectedDepot == null)
                ? null
                : _calculate,
          ),
        ),
      ],
    );
  }

  Widget _buildResultsPanel() {
    final vehicle = _selectedVehicle!;
    final fuelPrice = _fuelPrices.priceForFuelType(vehicle.fuelType);

    return Column(
      crossAxisAlignment: CrossAxisAlignment.start,
      children: [
        Row(
          children: [
            _sectionTitle('Itinéraires'),
            const Spacer(),
            TextButton.icon(
              icon: const Icon(Icons.refresh, size: 16),
              label: const Text('Recalculer'),
              onPressed: () => setState(() {
                _routes = [];
                _selectedRoute = null;
              }),
            ),
          ],
        ),

        // Légende
        Row(children: [
          _legendDot(const Color(0xFF1565C0)),
          const SizedBox(width: 4),
          const Text('Avec péage', style: TextStyle(fontSize: 12)),
          const SizedBox(width: 16),
          _legendDot(const Color(0xFF2E7D32)),
          const SizedBox(width: 4),
          const Text('Sans péage', style: TextStyle(fontSize: 12)),
        ]),

        const SizedBox(height: 12),

        ..._routes.map((route) {
          final total = route.totalCost(
            consumptionPer100km: vehicle.consumptionPer100km,
            fuelPricePerLiter: fuelPrice,
            maintenanceCostPerKm: vehicle.maintenanceCostPerKm,
            nbTechnicians: _nbTechnicians,
            hourlyRate: _hourlyRate,
            freeZoneKm: _applyFreeZone ? _freeZoneKm : 0.0,
            freeZoneMinutes: _applyFreeZone ? _freeZoneMinutes.toDouble() : 0.0,
          );
          final fuel = route.fuelCost(
            consumptionPer100km: vehicle.consumptionPer100km,
            fuelPricePerLiter: fuelPrice,
            freeZoneKm: _applyFreeZone ? _freeZoneKm : 0.0,
          );
          final maint = route.maintenanceCost(
            costPerKm: vehicle.maintenanceCostPerKm,
            freeZoneKm: _applyFreeZone ? _freeZoneKm : 0.0,
          );
          final labor = route.laborCost(
            nbTechnicians: _nbTechnicians,
            hourlyRate: _hourlyRate,
            freeZoneMinutes: _applyFreeZone ? _freeZoneMinutes.toDouble() : 0.0,
          );

          final isToll = route.routeType == 'TOLL';
          final color = isToll
              ? const Color(0xFF1565C0)
              : const Color(0xFF2E7D32);

          return _buildRouteCard(
            route: route,
            color: color,
            label: isToll ? '🚗 Route la plus rapide' : '🛣️ Route sans péage',
            total: total,
            fuel: fuel,
            maint: maint,
            labor: labor,
          );
        }),
      ],
    );
  }

  Widget _buildRouteCard({
    required RouteResult route,
    required Color color,
    required String label,
    required double total,
    required double fuel,
    required double maint,
    required double labor,
  }) {
    return Container(
      margin: const EdgeInsets.only(bottom: 16),
      decoration: BoxDecoration(
        border: Border.all(color: color, width: 2),
        borderRadius: BorderRadius.circular(12),
      ),
      child: Column(
        children: [
          // En-tête
          Container(
            padding: const EdgeInsets.symmetric(horizontal: 16, vertical: 10),
            decoration: BoxDecoration(
              color: color.withValues(alpha: 0.08),
              borderRadius: const BorderRadius.vertical(top: Radius.circular(10)),
            ),
            child: Row(
              children: [
                Text(
                  label,
                  style: TextStyle(
                    fontWeight: FontWeight.bold,
                    color: color,
                    fontSize: 14,
                  ),
                ),
                const Spacer(),
                Text(
                  _formatDistance(route.distanceMeters),
                  style: TextStyle(color: color, fontWeight: FontWeight.w600),
                ),
                const SizedBox(width: 8),
                Text(
                  _formatDuration(route.durationSeconds),
                  style: TextStyle(color: color),
                ),
              ],
            ),
          ),

          // Détail des coûts
          Padding(
            padding: const EdgeInsets.all(14),
            child: Column(
              children: [
                _costRow('⛽ Carburant', fuel),
                _costRow('🔧 Maintenance', maint),
                _costRow('👷 Main-d\'œuvre (×$_nbTechnicians)', labor),
                if (route.tollCost > 0) _costRow('🛣️ Péage', route.tollCost),
                const Divider(),
                _costRow('Total', total, bold: true, large: true),
              ],
            ),
          ),

          // Bouton Sélectionner
          Padding(
            padding: const EdgeInsets.fromLTRB(14, 0, 14, 14),
            child: SizedBox(
              width: double.infinity,
              child: ElevatedButton(
                style: ElevatedButton.styleFrom(
                  backgroundColor: color,
                  foregroundColor: Colors.white,
                ),
                onPressed: () => _selectRoute(route),
                child: Text(
                  'Sélectionner — ${total.toStringAsFixed(2)} €',
                  style: const TextStyle(fontWeight: FontWeight.bold),
                ),
              ),
            ),
          ),
        ],
      ),
    );
  }

  Widget _costRow(String label, double amount,
      {bool bold = false, bool large = false}) {
    final style = TextStyle(
      fontWeight: bold ? FontWeight.bold : FontWeight.normal,
      fontSize: large ? 15 : 13,
    );
    return Padding(
      padding: const EdgeInsets.symmetric(vertical: 2),
      child: Row(
        mainAxisAlignment: MainAxisAlignment.spaceBetween,
        children: [
          Text(label, style: style),
          Text('${amount.toStringAsFixed(2)} €',
              style: style.copyWith(
                  color: bold ? AppColors.rouge : Colors.black87)),
        ],
      ),
    );
  }

  Widget _legendDot(Color color) => Container(
        width: 14,
        height: 14,
        decoration: BoxDecoration(color: color, shape: BoxShape.circle),
      );

  Widget _sectionTitle(String title) => Padding(
        padding: const EdgeInsets.only(bottom: 8),
        child: Text(title,
            style: const TextStyle(fontWeight: FontWeight.bold, fontSize: 14)),
      );

  Widget _emptyHint(String msg) => Container(
        padding: const EdgeInsets.all(12),
        decoration: BoxDecoration(
          color: Colors.orange[50],
          borderRadius: BorderRadius.circular(8),
          border: Border.all(color: Colors.orange[200]!),
        ),
        child:
            Row(children: [const Icon(Icons.info_outline, color: Colors.orange), const SizedBox(width: 8), Expanded(child: Text(msg, style: const TextStyle(fontSize: 12)))]),
      );
}
