// SPDX-FileCopyrightText: © 2025 Nøkken.io <nokken.io@proton.me>
// SPDX-License-Identifier: AGPL-3.0
//
//  calendar_day_cell.dart
//  Reusable calendar day cell for medical and mood calendars

import 'package:flutter/material.dart';
import 'package:nokken/src/core/ui/theme/app_colors.dart';
import 'package:nokken/src/core/ui/theme/app_theme.dart';
import 'package:nokken/src/core/utils/get_icons_colors.dart';
import 'package:nokken/src/features/bloodwork_tracker/models/bloodwork.dart';
import 'package:nokken/src/features/mood_tracker/models/mood_entry.dart';
import 'package:nokken/src/features/mood_tracker/utils/mood_utils.dart';

/// A reusable widget for rendering calendar day cells with different styles based on events
class CalendarDayCell extends StatelessWidget {
  final DateTime day;
  final bool isSelected;
  final bool isToday;
  final bool isOutsideMonth;
  final AppointmentType? appointmentType;
  final bool hasInjection;
  final bool hasPatch;
  final bool hasOral;
  final bool hasTopical;
  final MoodRating? moodRating;
  final bool isMoodView;

  /// Creates a calendar day cell with appropriate styling based on medical/mood events
  const CalendarDayCell({
    super.key,
    required this.day,
    this.isSelected = false,
    this.isToday = false,
    this.isOutsideMonth = false,
    this.appointmentType,
    this.hasInjection = false,
    this.hasPatch = false,
    this.hasOral = false,
    this.hasTopical = false,
    this.moodRating,
    this.isMoodView = false,
  });

  @override
  Widget build(BuildContext context) {
    // Calculate border color based on event type and view mode
    Color borderColor = _calculateBorderColor();

    // Calculate text color based on event type, view mode, and cell selection state
    Color textColor = _calculateTextColor(borderColor);

    // Apply alpha for outside month dates
    if (isOutsideMonth) {
      borderColor = borderColor.withAlpha(160);
      textColor = textColor.withAlpha(isSelected ? 255 : 160);
    }

    // Calculate the background color for the cell
    Color backgroundColor = _calculateBackgroundColor(borderColor);

    // Build the cell with appropriate styling
    return Container(
      margin: const EdgeInsets.all(4),
      decoration: BoxDecoration(
        shape: BoxShape.circle,
        color: backgroundColor,
        border: _hasMedicalOrMoodIndicator()
            ? Border.all(color: borderColor, width: 2)
            : (isToday
                ? Border.all(color: AppColors.primary, width: 1.5)
                : null),
      ),
      child: Center(
        child: Text(
          '${day.day}',
          style: TextStyle(
            color: textColor,
            fontWeight: _hasMedicalOrMoodIndicator() || isSelected || isToday
                ? FontWeight.bold
                : FontWeight.normal,
          ),
        ),
      ),
    );
  }

  /// Determines if the cell has any medical or mood indicators
  bool _hasMedicalOrMoodIndicator() {
    if (isMoodView) {
      return moodRating != null;
    } else {
      return hasInjection ||
          hasPatch ||
          hasOral ||
          hasTopical ||
          appointmentType != null;
    }
  }

  /// Calculates the border color based on cell state and event type
  Color _calculateBorderColor() {
    if (isMoodView) {
      return moodRating != null
          ? MoodUtils.getMoodColor(moodRating!)
          : AppColors.primary;
    } else {
      if (appointmentType != null) {
        return GetIconsColors.getAppointmentColor(appointmentType!);
      } else if (hasInjection) {
        return AppColors.injection;
      } else if (hasPatch) {
        return AppColors.patch;
      } else if (hasOral) {
        return AppColors.oralMedication;
      } else if (hasTopical) {
        return AppColors.topical;
      }
      return AppColors.primary;
    }
  }

  /// Calculates the text color based on cell state
  Color _calculateTextColor(Color borderColor) {
    if (isSelected) {
      return AppColors.onPrimary;
    } else if (isToday) {
      return _hasMedicalOrMoodIndicator() ? borderColor : AppColors.primary;
    } else if (_hasMedicalOrMoodIndicator()) {
      return borderColor;
    } else if (isOutsideMonth) {
      return AppTheme.white.withAlpha(100);
    }
    return AppTheme.white;
  }

  /// Calculates the background color based on cell state
  Color _calculateBackgroundColor(Color borderColor) {
    if (isSelected) {
      return _hasMedicalOrMoodIndicator() ? borderColor : AppColors.primary;
    } else if (isToday) {
      return AppColors.primary.withAlpha(40);
    }
    return Colors.transparent;
  }
}
