import 'package:intl/intl.dart';
import 'package:prosapp_web_app/models/profesional.dart';
import 'package:prosapp_web_app/models/schedules_entity.dart';
import 'package:prosapp_web_app/models/service.dart';
import 'package:prosapp_web_app/models/usuario.dart';
import 'package:prosapp_web_app/providers/auth_provider.dart';
import 'package:prosapp_web_app/providers/professional_form_provider.dart';
import 'package:prosapp_web_app/providers/professional_provider.dart';
import 'package:prosapp_web_app/providers/services_provider.dart';
import 'package:prosapp_web_app/ui/cards/white_card.dart';
import 'package:prosapp_web_app/utils/time_of_day_utils.dart';
import 'package:provider/provider.dart';
import 'package:table_calendar/table_calendar.dart';
import 'package:flutter/material.dart';

class ProfessionalCalendarView extends StatefulWidget {
  const ProfessionalCalendarView({super.key});

  @override
  State<ProfessionalCalendarView> createState() =>
      _ProfessionalCalendarViewState();
}

class _ProfessionalCalendarViewState extends State<ProfessionalCalendarView> {
  DateTime today = DateTime.now();
  late int numDay;

  List<Service>? _services;

  Usuario? user;

  @override
  void initState() {
    super.initState();
    numDay = today.weekday;
    _fetchProfessionalAndServices();
  }

  void _fetchProfessionalAndServices() async {
    final authProvider = Provider.of<AuthProvider>(context, listen: false);
    final professionalFormProvider = Provider.of<ProfessionalFormProvider>(context, listen: false);
    final servicesProvider = Provider.of<ServicesProvider>(context, listen: false);



    final proProvider = Provider.of<ProfessionalProvider>(context, listen: false);

    final professional = await proProvider.getProfessional(authProvider.user!.id);
    professionalFormProvider.setProfesional(professional);

    final services = await servicesProvider.getServicesForProfessional(professional.id);
    setState(() {
      _services = services;
      user = authProvider.user;
    });
  }

  void _onDaySelected(DateTime day, DateTime focusedDay) {
    setState(() {
      today = day;
      numDay = today.weekday;
    });
    _fetchProfessionalAndServices();
  }

  @override
  Widget build(BuildContext context) {
    return Consumer<ProfessionalFormProvider>(
      builder: (context, professionalFormProvider, child) {
        if (professionalFormProvider.profesional == null) {
          return const Center(
            child: CircularProgressIndicator(),
          );
        }

        final profesional = professionalFormProvider.profesional!;

        return ListView(
          physics: const ClampingScrollPhysics(),
          children: [
            Center(
              child: ConstrainedBox(
                constraints: const BoxConstraints(maxWidth: 900),
                child: WhiteCard(
                  title: 'Calendario',
                  child: Column(
                    children: [
                      TableCalendar(
                        locale: 'es_CO',
                        firstDay: DateTime.now(),
                        lastDay: DateTime.utc(2030, 3, 14),
                        focusedDay: today,
                        availableGestures: AvailableGestures.all,
                        onDaySelected: _onDaySelected,
                        selectedDayPredicate: (day) => isSameDay(day, today),
                      ),
                      const Divider(height: 0),
                      SizedBox(
                        width: double.infinity,
                        child: Padding(
                          padding: const EdgeInsets.symmetric(
                            horizontal: 15,
                            vertical: 8,
                          ),
                          child: Text(
                            DateFormat('dd MMMM yyyy', 'es').format(today),
                            style: const TextStyle(
                              color: Colors.black,
                              fontSize: 16,
                              fontWeight: FontWeight.w600,
                            ),
                          ),
                        ),
                      ),
                      const Divider(height: 0),
                      Column(
                        children: [
                          ..._rangesItems(_getScheduleFromNumDay(numDay, profesional),context),
                        ],
                      ),
                    ],
                  ),
                ),
              ),
            ),
          ],
        );
      },
    );
  }

  ScheduleEntity? _getScheduleFromNumDay(int numDay, Profesional userProfessional) {
    switch (numDay) {
      case 1:
        return userProfessional.schedules.monday;
      case 2:
        return userProfessional.schedules.tuesday;
      case 3:
        return userProfessional.schedules.wednesday;
      case 4:
        return userProfessional.schedules.thursday;
      case 5:
        return userProfessional.schedules.friday;
      case 6:
        return userProfessional.schedules.saturday;
      case 7:
        return userProfessional.schedules.sunday;
      default:
        return null;
    }
  }

  List<Widget> _rangesItems(ScheduleEntity? schedule, BuildContext context) {
    if (schedule == null ||
        !schedule.enabled ||
        schedule.range1Hour1 == null ||
        schedule.range2Hour2 == null) {
      return [
        const Padding(
          padding: EdgeInsets.symmetric(vertical: 25),
          child: Text("No hay horarios disponibles"),
        )
      ];
    }

    if (schedule.continuousDay) {
      List<TimeOfDay> ranges = TimeOfDayUtils.genRanges(
        schedule.range1Hour1!,
        schedule.range2Hour2!,
      );

      return rangesItemList(ranges, _services, today, context);
    }

    List<TimeOfDay> ranges1 = TimeOfDayUtils.genRanges(
      schedule.range1Hour1!,
      schedule.range1Hour2!,
    );
    List<TimeOfDay> ranges2 = TimeOfDayUtils.genRanges(
      schedule.range2Hour1!,
      schedule.range2Hour2!,
    );

    return [
      ...rangesItemList(ranges1, _services, today, context),
      ...rangesItemList(ranges2, _services, today, context),
    ];
  }

  bool _isHora1Ocupada(
      TimeOfDay hora1, List<Service>? events, DateTime selectedDay) {
    if (events != null) {
      for (Service event in events) {
        if (selectedDay.toIso8601String().split('T').first == event.day) {
          if (hora1 == event.range1Hour1) {
            return true;
          }
        }
      }
    }
    return false;
  }

  List<Widget> rangesItemList(List<TimeOfDay> ranges, List<Service>? events,
      DateTime selectedDay, BuildContext context) {
    return ranges.map((time) {
      if (_isHora1Ocupada(time, events, selectedDay)) {
        return Card(
          elevation: 4,
          margin: const EdgeInsets.symmetric(vertical: 5, horizontal: 10),
          shape: RoundedRectangleBorder(
            borderRadius: BorderRadius.circular(10),
          ),
          child: ListTile(
            onTap: () {
              if (events != null) {
                for (Service event in events) {
                  if (selectedDay.toIso8601String().split('T').first ==
                      event.day) {
                    if (time == event.range1Hour1) {
                      if (event.userId == event.professionalId) {
                        ScaffoldMessenger.of(context).clearSnackBars();
                        ScaffoldMessenger.of(context).showSnackBar(
                          const SnackBar(
                            content: Text('Horario ocupado por ti'),
                          ),
                        );
                      } else {
                        // Navigator.push(
                        //   context,
                        //   CupertinoPageRoute(
                        //     builder: (context) => ProfessionalServiceScreen(
                        //       serviceId: event.id!,
                        //     ),
                        //   ),
                        // );
                      }
                    }
                  }
                }
              }
            },
            contentPadding: const EdgeInsets.all(16),
            leading: Container(
              width: 40,
              height: 40,
              decoration: const BoxDecoration(
                gradient: LinearGradient(
                  colors: [Colors.yellow, Colors.red, Colors.red],
                  begin: Alignment.topLeft,
                  end: Alignment.bottomRight,
                ),
                shape: BoxShape.circle,
              ),
              child: const Center(
                child: Icon(
                  Icons.access_time,
                  color: Colors.white,
                ),
              ),
            ),
            title: Text(
              ScheduleEntity.getFormatTime(time) ?? '',
              style: const TextStyle(fontSize: 15, fontWeight: FontWeight.bold),
            ),
            subtitle: const Text(
              'Ocupado',
              style: TextStyle(
                  color: Colors.red, fontSize: 13, fontWeight: FontWeight.bold),
            ),
          ),
        );
      } else {
        return Card(
          elevation: 4,
          margin: const EdgeInsets.symmetric(vertical: 5, horizontal: 10),
          shape: RoundedRectangleBorder(
            borderRadius: BorderRadius.circular(10),
          ),
          child: ListTile(
            onTap: () {
              showDialog(
                context: context,
                builder: (BuildContext dialogContext) {
                  return AlertDialog(
                    title: const Text('Reservar hora'),
                    content: Column(
                      mainAxisSize: MainAxisSize.min,
                      children: [
                        Text(
                          '¿Estás seguro de que deseas reservar a las ${ScheduleEntity.getFormatTime(time)} del ${DateFormat('dd-MM-yyyy').format(today)}?',
                        ),
                        const SizedBox(height: 10),
                        const Text(
                          '⚠️ Esta acción no se puede deshacer ⚠️',
                          style: TextStyle(fontWeight: FontWeight.bold),
                        ),
                      ],
                    ),
                    actions: [
                      TextButton(
                        onPressed: () {
                          Navigator.pop(dialogContext);
                        },
                        child: const Text('No, cancelar'),
                      ),
                      TextButton(
                        onPressed: () {
                          Navigator.pop(dialogContext);

                          Navigator.pop(context);
                        },
                        child: const Text('Sí, reservar'),
                      ),
                    ],
                  );
                },
              );
            },
            contentPadding: const EdgeInsets.all(16),
            leading: Container(
              width: 40,
              height: 40,
              decoration: const BoxDecoration(
                gradient: LinearGradient(
                  colors: [Colors.blue, Colors.green],
                  begin: Alignment.topLeft,
                  end: Alignment.bottomRight,
                ),
                shape: BoxShape.circle,
              ),
              child: const Center(
                child: Icon(
                  Icons.access_time,
                  color: Colors.white,
                ),
              ),
            ),
            title: Text(
              ScheduleEntity.getFormatTime(time) ?? '',
              style: const TextStyle(fontSize: 15, fontWeight: FontWeight.bold),
            ),
            subtitle: const Text(
              'Disponible',
              style: TextStyle(
                color: Colors.green,
                fontSize: 13,
                fontWeight: FontWeight.bold,
              ),
            ),
          ),
        );
      }
    }).toList();
  }
}
