import 'package:flutter/material.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'package:shadcn_ui/shadcn_ui.dart';

import '../../core/api_client.dart';
import '../../core/app_colors.dart';
import '../../core/app_design_tokens.dart';
import '../../core/app_theme.dart';
import '../../core/navigation_provider.dart';
import '../../providers/data_providers.dart';
import '../../widgets/app_error_state.dart';
import '../../widgets/app_toast.dart';
import '../../widgets/common_widgets.dart';
import '../care_plan_ui_logic.dart';
import 'medication_ui_logic.dart';

class MedicationEditPage extends ConsumerStatefulWidget {
  final String? id;

  const MedicationEditPage({super.key, this.id});

  @override
  ConsumerState<MedicationEditPage> createState() => _MedicationEditPageState();
}

class _MedicationEditPageState extends ConsumerState<MedicationEditPage> {
  final _nameController = TextEditingController();
  final _dosageController = TextEditingController();
  final _notesController = TextEditingController();
  List<TimeOfDay> _times = [
    const TimeOfDay(hour: 8, minute: 0),
    const TimeOfDay(hour: 18, minute: 0),
  ];
  DateTime _startDate = DateTime.now();
  DateTime? _endDate;
  bool _saving = false;
  bool _loading = false;
  String? _loadError;

  bool get _editing => widget.id?.isNotEmpty == true;

  @override
  void initState() {
    super.initState();
    if (_editing) _load();
  }

  @override
  void dispose() {
    _nameController.dispose();
    _dosageController.dispose();
    _notesController.dispose();
    super.dispose();
  }

  Future<void> _load() async {
    setState(() {
      _loading = true;
      _loadError = null;
    });
    try {
      final medications = await ref.read(medicationServiceProvider).getList();
      final medication = medications.cast<Map<String, dynamic>?>().firstWhere(
        (item) => item?['id']?.toString() == widget.id,
        orElse: () => null,
      );
      if (medication == null) throw const ApiException('该用药记录不存在');
      _nameController.text = medication['name']?.toString() ?? '';
      _dosageController.text = medication['dosage']?.toString() ?? '';
      _notesController.text = medication['notes']?.toString() ?? '';
      final loadedTimes =
          (medication['timeOfDay'] as List?)
              ?.map((value) => _parseTime(value))
              .whereType<TimeOfDay>()
              .toList() ??
          [];
      if (loadedTimes.isNotEmpty) _times = loadedTimes;
      _startDate =
          DateTime.tryParse(medication['startDate']?.toString() ?? '') ??
          DateTime.now();
      _endDate = DateTime.tryParse(medication['endDate']?.toString() ?? '');
    } catch (error) {
      _loadError = error is ApiException ? error.message : '用药信息加载失败';
    } finally {
      if (mounted) setState(() => _loading = false);
    }
  }

  Future<void> _save() async {
    final timeValues = _times.map(_timeValue).toList();
    final validation = validateMedicationForm(
      name: _nameController.text,
      dosage: _dosageController.text,
      times: timeValues,
      startDate: _startDate,
      endDate: _endDate,
    );
    if (validation != null) {
      AppToast.show(context, validation, type: AppToastType.warning);
      return;
    }
    setState(() => _saving = true);
    final payload = <String, dynamic>{
      'name': _nameController.text.trim(),
      'dosage': _dosageController.text.trim(),
      'frequency': _frequencyForTimes(_times.length),
      'notes': _notesController.text.trim(),
      'timeOfDay': timeValues,
      'startDate': _dateValue(_startDate),
      'endDate': _endDate == null ? null : _dateValue(_endDate!),
      'source': 'Manual',
    };
    try {
      final service = ref.read(medicationServiceProvider);
      if (_editing) {
        await service.update(widget.id!, payload);
      } else {
        await service.create(payload);
      }
      ref.invalidate(medicationListProvider);
      ref.invalidate(medicationReminderProvider);
      if (mounted) {
        AppToast.show(
          context,
          _editing ? '用药已更新' : '用药已添加',
          type: AppToastType.success,
        );
        popRoute(ref);
      }
    } catch (error) {
      if (mounted) {
        AppToast.show(
          context,
          error is ApiException ? error.message : '保存失败，请稍后重试',
          type: AppToastType.error,
        );
      }
    } finally {
      if (mounted) setState(() => _saving = false);
    }
  }

  Future<void> _deleteMedication() async {
    if (!_editing || _saving) return;
    final confirmed = await showDialog<bool>(
      context: context,
      builder: (dialogContext) => AlertDialog(
        title: const Text('删除用药'),
        content: Text('确定删除“${_nameController.text.trim()}”吗？相关服药记录也将一并删除。'),
        actions: [
          TextButton(
            onPressed: () => Navigator.pop(dialogContext, false),
            child: const Text('取消'),
          ),
          TextButton(
            onPressed: () => Navigator.pop(dialogContext, true),
            style: TextButton.styleFrom(foregroundColor: AppColors.errorText),
            child: const Text('删除'),
          ),
        ],
      ),
    );
    if (confirmed != true || !mounted) return;
    setState(() => _saving = true);
    try {
      await ref.read(medicationServiceProvider).deleteMedication(widget.id!);
      ref.invalidate(medicationListProvider);
      ref.invalidate(medicationReminderProvider);
      if (mounted) {
        AppToast.show(context, '用药已删除', type: AppToastType.success);
        popRoute(ref);
      }
    } catch (error) {
      if (mounted) {
        AppToast.show(
          context,
          error is ApiException ? error.message : '删除失败，请稍后重试',
          type: AppToastType.error,
        );
      }
    } finally {
      if (mounted) setState(() => _saving = false);
    }
  }

  @override
  Widget build(BuildContext context) {
    return GradientScaffold(
      appBar: AppBar(
        leading: IconButton(
          icon: const Icon(Icons.arrow_back),
          onPressed: () => popRoute(ref),
        ),
        title: Text(_editing ? '编辑用药' : '添加用药'),
      ),
      bottomNavigationBar: _loading || _loadError != null
          ? null
          : SafeArea(
              top: false,
              child: Container(
                color: Colors.white,
                padding: const EdgeInsets.fromLTRB(16, 12, 16, 12),
                child: AppGradientOutlineButton(
                  label: _editing ? '保存修改' : '添加用药',
                  onPressed: _saving ? null : _save,
                  loading: _saving,
                ),
              ),
            ),
      body: _loading
          ? const Center(child: CircularProgressIndicator())
          : _loadError != null
          ? AppErrorState(title: _loadError!, onRetry: _load)
          : ListView(
              keyboardDismissBehavior: ScrollViewKeyboardDismissBehavior.onDrag,
              padding: const EdgeInsets.fromLTRB(16, 12, 16, 28),
              children: [
                _FormSection(
                  title: '药品信息',
                  children: [
                    _TextFieldRow(
                      label: '药品名称',
                      controller: _nameController,
                      hint: '请输入药品名称',
                    ),
                    const _SectionDivider(),
                    _TextFieldRow(
                      label: '剂量',
                      controller: _dosageController,
                      hint: '例如 100 mg',
                    ),
                  ],
                ),
                const SizedBox(height: 16),
                _FormSection(
                  title: '服用安排',
                  children: [
                    _PickerRow(
                      label: '每日次数',
                      value: '${_times.length}次',
                      onTap: _pickCount,
                    ),
                    const _SectionDivider(),
                    Padding(
                      padding: const EdgeInsets.fromLTRB(16, 11, 12, 11),
                      child: Row(
                        children: [
                          const Text('服药时间', style: AppTextStyles.formLabel),
                          const SizedBox(width: 12),
                          Expanded(
                            child: Wrap(
                              alignment: WrapAlignment.end,
                              spacing: 8,
                              runSpacing: 8,
                              children: List.generate(
                                _times.length,
                                (index) => _TimeButton(
                                  value: _timeValue(_times[index]),
                                  onTap: () => _pickTime(index),
                                ),
                              ),
                            ),
                          ),
                        ],
                      ),
                    ),
                  ],
                ),
                const SizedBox(height: 16),
                _FormSection(
                  title: '用药周期',
                  children: [
                    _PickerRow(
                      label: '开始日期',
                      value: _displayDate(_startDate),
                      onTap: _pickStartDate,
                    ),
                    const _SectionDivider(),
                    _PickerRow(
                      label: '结束日期',
                      value: _endDate == null ? '长期' : _displayDate(_endDate!),
                      onTap: _pickEndDate,
                      onClear: _endDate == null
                          ? null
                          : () => setState(() => _endDate = null),
                    ),
                  ],
                ),
                const SizedBox(height: 16),
                _FormSection(
                  title: '备注',
                  children: [
                    Padding(
                      padding: const EdgeInsets.all(16),
                      child: TextField(
                        controller: _notesController,
                        minLines: 3,
                        maxLines: 5,
                        maxLength: 200,
                        decoration: const InputDecoration(
                          hintText: '可填写饭前、饭后或其他用药要求（选填）',
                          border: InputBorder.none,
                          enabledBorder: InputBorder.none,
                          focusedBorder: InputBorder.none,
                          filled: false,
                          contentPadding: EdgeInsets.zero,
                        ),
                      ),
                    ),
                  ],
                ),
                if (_editing) ...[
                  const SizedBox(height: 16),
                  Material(
                    color: Colors.white,
                    borderRadius: AppRadius.lgBorder,
                    clipBehavior: Clip.antiAlias,
                    child: InkWell(
                      onTap: _saving ? null : _deleteMedication,
                      child: const SizedBox(
                        height: 54,
                        child: Center(
                          child: Text(
                            '删除用药',
                            style: TextStyle(
                              color: AppColors.errorText,
                              fontSize: 15,
                              fontWeight: FontWeight.w700,
                            ),
                          ),
                        ),
                      ),
                    ),
                  ),
                ],
              ],
            ),
    );
  }

  Future<void> _pickCount() async {
    final count = await showAppCountPicker(
      context,
      initialValue: _times.length,
      min: 1,
      max: 4,
      label: '次',
    );
    if (count == null || !mounted) return;
    setState(() {
      while (_times.length < count) {
        final hour = (8 + _times.length * 5).clamp(0, 23);
        _times.add(TimeOfDay(hour: hour, minute: 0));
      }
      while (_times.length > count) {
        _times.removeLast();
      }
    });
  }

  Future<void> _pickTime(int index) async {
    final value = await showAppTimePicker(context, initialTime: _times[index]);
    if (value != null && mounted) setState(() => _times[index] = value);
  }

  Future<void> _pickStartDate() async {
    final value = await showAppDatePicker(
      context,
      initialDate: _startDate,
      firstDate: DateTime(2020),
      lastDate: DateTime(2035),
    );
    if (value != null && mounted) setState(() => _startDate = value);
  }

  Future<void> _pickEndDate() async {
    final value = await showAppDatePicker(
      context,
      initialDate: _endDate ?? _startDate,
      firstDate: DateTime(2020),
      lastDate: DateTime(2035),
    );
    if (value != null && mounted) setState(() => _endDate = value);
  }
}

class _FormSection extends StatelessWidget {
  final String title;
  final List<Widget> children;

  const _FormSection({required this.title, required this.children});

  @override
  Widget build(BuildContext context) {
    return Column(
      crossAxisAlignment: CrossAxisAlignment.start,
      children: [
        Padding(
          padding: const EdgeInsets.only(left: 2, bottom: 8),
          child: Text(
            title,
            style: AppTextStyles.sectionTitle.copyWith(fontSize: 16),
          ),
        ),
        Container(
          clipBehavior: Clip.antiAlias,
          decoration: BoxDecoration(
            color: Colors.white,
            borderRadius: AppRadius.lgBorder,
          ),
          child: Column(children: children),
        ),
      ],
    );
  }
}

class _TextFieldRow extends StatelessWidget {
  final String label;
  final TextEditingController controller;
  final String hint;

  const _TextFieldRow({
    required this.label,
    required this.controller,
    required this.hint,
  });

  @override
  Widget build(BuildContext context) {
    return Padding(
      padding: const EdgeInsets.symmetric(horizontal: 16, vertical: 4),
      child: Row(
        children: [
          SizedBox(
            width: 82,
            child: Text(label, style: AppTextStyles.formLabel),
          ),
          Expanded(
            child: TextField(
              controller: controller,
              textAlign: TextAlign.right,
              decoration: InputDecoration(
                hintText: hint,
                border: InputBorder.none,
                enabledBorder: InputBorder.none,
                focusedBorder: InputBorder.none,
                filled: false,
                contentPadding: const EdgeInsets.symmetric(vertical: 14),
              ),
              style: AppTextStyles.formValue,
            ),
          ),
        ],
      ),
    );
  }
}

class _PickerRow extends StatelessWidget {
  final String label;
  final String value;
  final VoidCallback onTap;
  final VoidCallback? onClear;

  const _PickerRow({
    required this.label,
    required this.value,
    required this.onTap,
    this.onClear,
  });

  @override
  Widget build(BuildContext context) {
    return InkWell(
      onTap: onTap,
      child: Padding(
        padding: const EdgeInsets.fromLTRB(16, 15, 10, 15),
        child: Row(
          children: [
            Expanded(child: Text(label, style: AppTextStyles.formLabel)),
            Text(value, style: AppTextStyles.formValue),
            if (onClear != null)
              IconButton(
                tooltip: '清除结束日期',
                visualDensity: VisualDensity.compact,
                onPressed: onClear,
                icon: const Icon(Icons.close, size: 18),
              )
            else
              const Padding(
                padding: EdgeInsets.only(left: 6),
                child: Icon(
                  LucideIcons.chevronRight,
                  color: AppColors.textHint,
                  size: 20,
                ),
              ),
          ],
        ),
      ),
    );
  }
}

class _TimeButton extends StatelessWidget {
  final String value;
  final VoidCallback onTap;

  const _TimeButton({required this.value, required this.onTap});

  @override
  Widget build(BuildContext context) {
    return OutlinedButton.icon(
      onPressed: onTap,
      icon: const Icon(LucideIcons.clock, size: 18),
      label: Text(value),
      style: OutlinedButton.styleFrom(
        foregroundColor: AppColors.primary,
        side: BorderSide(color: AppColors.primary.withValues(alpha: 0.38)),
        shape: RoundedRectangleBorder(borderRadius: AppRadius.smBorder),
        padding: const EdgeInsets.symmetric(horizontal: 14, vertical: 11),
      ),
    );
  }
}

class _SectionDivider extends StatelessWidget {
  const _SectionDivider();

  @override
  Widget build(BuildContext context) {
    return const Padding(
      padding: EdgeInsets.only(left: 16),
      child: Divider(height: 1, thickness: 0.7, color: AppColors.divider),
    );
  }
}

TimeOfDay? _parseTime(Object value) {
  final parts = value.toString().split(':');
  if (parts.length < 2) return null;
  final hour = int.tryParse(parts[0]);
  final minute = int.tryParse(parts[1]);
  if (hour == null || minute == null) return null;
  return TimeOfDay(hour: hour, minute: minute);
}

String _timeValue(TimeOfDay value) =>
    '${value.hour.toString().padLeft(2, '0')}:${value.minute.toString().padLeft(2, '0')}';

String _dateValue(DateTime value) =>
    '${value.year}-${value.month.toString().padLeft(2, '0')}-${value.day.toString().padLeft(2, '0')}';

String _displayDate(DateTime value) => formatMedicationFormDate(value);

String _frequencyForTimes(int count) => switch (count) {
  2 => 'TwiceDaily',
  3 => 'ThreeTimesDaily',
  _ => 'Daily',
};
