import { ROUTES } from '@/constants/Routes';
import { useAppDispatch, useAppSelector } from '@/hooks/redux';
import { useI18n } from '@/hooks/useI18n';
import { ChallengeType } from '@/services/challengesApi';
import { reportChallengeProgress, selectChallengeList } from '@/store/challengesSlice';
import { ActivityRingsData, fetchActivityRingsForDate } from '@/utils/health';
import { logger } from '@/utils/logger';
import { useFocusEffect } from '@react-navigation/native';
import dayjs from 'dayjs';
import { router } from 'expo-router';
import React, { useCallback, useEffect, useMemo, useRef, useState } from 'react';
import { StyleSheet, Text, TouchableOpacity, View } from 'react-native';
import { CircularRing } from './CircularRing';

type FitnessRingsCardProps = {
  style?: any;
  selectedDate?: Date;
  // 动画重置令牌
  resetToken?: unknown;
};

/**
 * 健身圆环卡片组件，模仿 Apple Watch 的健身圆环
 */
export function FitnessRingsCard({
  style,
  selectedDate,
  resetToken,
}: FitnessRingsCardProps) {
  const { t } = useI18n();
  const dispatch = useAppDispatch();
  const challenges = useAppSelector(selectChallengeList);
  const [activityData, setActivityData] = useState<ActivityRingsData | null>(null);
  const [loading, setLoading] = useState(false);
  const loadingRef = useRef(false);
  const lastReportedRef = useRef<{ date: string } | null>(null);

  const joinedExerciseChallenges = useMemo(
    () => challenges.filter((challenge) => challenge.type === ChallengeType.EXERCISE && challenge.isJoined && challenge.status === 'ongoing'),
    [challenges]
  );

  // 获取健身圆环数据 - 在页面聚焦、日期变化、从后台切换到前台时触发
  useFocusEffect(
    useCallback(() => {
      const loadActivityData = async () => {
        if (!selectedDate) return;

        // 防止重复请求
        if (loadingRef.current) return;

        try {
          loadingRef.current = true;
          setLoading(true);
          const data = await fetchActivityRingsForDate(selectedDate);
          setActivityData(data);
        } catch (error) {
          console.error('FitnessRingsCard: 获取健身圆环数据失败:', error);
          setActivityData(null);
        } finally {
          setLoading(false);
          loadingRef.current = false;
        }
      };

      loadActivityData();
    }, [selectedDate])
  );

  useEffect(() => {
    if (!selectedDate || !activityData || !joinedExerciseChallenges.length) {
      return;
    }

    if (!dayjs(selectedDate).isSame(dayjs(), 'day')) {
      return;
    }

    const {
      activeEnergyBurned,
      activeEnergyBurnedGoal,
      appleExerciseTime,
      appleExerciseTimeGoal,
      appleStandHours,
      appleStandHoursGoal,
    } = activityData;

    if (
      activeEnergyBurnedGoal <= 0 ||
      appleExerciseTimeGoal <= 0 ||
      appleStandHoursGoal <= 0
    ) {
      return;
    }

    const allRingsClosed =
      activeEnergyBurned >= activeEnergyBurnedGoal &&
      appleExerciseTime >= appleExerciseTimeGoal &&
      appleStandHours >= appleStandHoursGoal;

    if (!allRingsClosed) {
      return;
    }

    const dateKey = dayjs(selectedDate).format('YYYY-MM-DD');
    if (lastReportedRef.current?.date === dateKey) {
      return;
    }

    const exerciseChallenge = joinedExerciseChallenges[0];
    if (!exerciseChallenge) {
      return;
    }

    const reportProgressAsync = async () => {
      try {
        await dispatch(reportChallengeProgress({ id: exerciseChallenge.id, value: 1 })).unwrap();
        lastReportedRef.current = { date: dateKey };
      } catch (error) {
        logger.warn('FitnessRingsCard: 挑战进度上报失败', { error, challengeId: exerciseChallenge.id });
      }
    };

    reportProgressAsync();
  }, [activityData, dispatch, joinedExerciseChallenges, selectedDate]);

  // 使用获取到的数据或默认值
  const activeCalories = activityData?.activeEnergyBurned ?? 0;
  const activeCaloriesGoal = activityData?.activeEnergyBurnedGoal ?? 350;
  const exerciseMinutes = activityData?.appleExerciseTime ?? 0;
  const exerciseMinutesGoal = activityData?.appleExerciseTimeGoal ?? 30;
  const standHours = activityData?.appleStandHours ?? 0;
  const standHoursGoal = activityData?.appleStandHoursGoal ?? 12;

  // 计算进度百分比
  const caloriesProgress = Math.min(1, Math.max(0, activeCalories / activeCaloriesGoal));
  const exerciseProgress = Math.min(1, Math.max(0, exerciseMinutes / exerciseMinutesGoal));
  const standProgress = Math.min(1, Math.max(0, standHours / standHoursGoal));

  const units = useMemo(
    () => ({
      kcal: t('statistics.components.fitness.kcal'),
      minutes: t('statistics.components.fitness.minutes'),
      hours: t('statistics.components.fitness.hours'),
    }),
    [t]
  );

  const fitnessRows = useMemo(
    () => [
      { key: 'active', value: Math.round(activeCalories), goal: activeCaloriesGoal, unit: units.kcal },
      { key: 'exercise', value: Math.round(exerciseMinutes), goal: exerciseMinutesGoal, unit: units.minutes },
      { key: 'stand', value: Math.round(standHours), goal: standHoursGoal, unit: units.hours },
    ],
    [activeCalories, activeCaloriesGoal, exerciseMinutes, exerciseMinutesGoal, standHours, standHoursGoal, units]
  );

  const handlePress = () => {
    router.push(ROUTES.FITNESS_RINGS_DETAIL);
  };

  return (
    <TouchableOpacity style={[styles.container, style]} onPress={handlePress}>
      <View style={styles.contentContainer}>
        {/* 左侧圆环 */}
        <View style={styles.ringsContainer}>
          <View style={styles.ringWrapper}>
            {/* 外圈 - 活动卡路里 (红色) */}
            <View style={[styles.ringPosition]}>
              <CircularRing
                size={36}
                strokeWidth={2.5}
                trackColor="rgba(255, 59, 48, 0.15)"
                progressColor="#FF3B30"
                progress={caloriesProgress}
                showCenterText={false}
                resetToken={resetToken}
                startAngleDeg={-90}
              />
            </View>

            {/* 中圈 - 锻炼分钟 (橙色) */}
            <View style={[styles.ringPosition]}>
              <CircularRing
                size={26}
                strokeWidth={2}
                trackColor="rgba(255, 149, 0, 0.15)"
                progressColor="#FF9500"
                progress={exerciseProgress}
                showCenterText={false}
                resetToken={resetToken}
                startAngleDeg={-90}
              />
            </View>

            {/* 内圈 - 站立小时 (蓝色) */}
            <View style={[styles.ringPosition]}>
              <CircularRing
                size={16}
                strokeWidth={1.5}
                trackColor="rgba(0, 122, 255, 0.15)"
                progressColor="#007AFF"
                progress={standProgress}
                showCenterText={false}
                resetToken={resetToken}
                startAngleDeg={-90}
              />
            </View>
          </View>
        </View>

        {/* 右侧数据显示 */}
        <View style={styles.dataContainer}>
          {fitnessRows.map((row) => (
            <View key={row.key} style={styles.dataRow}>
              <Text style={styles.dataText}>
                {loading ? (
                  <Text style={styles.dataValue}>--</Text>
                ) : (
                  <>
                    <Text style={styles.dataValue}>{row.value}</Text>
                    <Text style={styles.dataGoal}>
                      {t('statistics.components.fitnessRings.goal', { goal: row.goal })}
                    </Text>
                  </>
                )}
              </Text>
              <Text style={styles.dataUnit}>{row.unit}</Text>
            </View>
          ))}
        </View>
      </View>
    </TouchableOpacity>
  );
}

const styles = StyleSheet.create({
  container: {
    borderRadius: 16,
    shadowColor: '#000',
    shadowOffset: {
      width: 0,
      height: 2,
    },
    shadowOpacity: 0.08,
    shadowRadius: 8,
    elevation: 3,
  },
  contentContainer: {
    flexDirection: 'row',
    alignItems: 'center',
    justifyContent: 'space-between',
  },
  ringsContainer: {
    alignItems: 'center',
    justifyContent: 'center',
    marginRight: 12,
  },
  ringWrapper: {
    position: 'relative',
    width: 36,
    height: 36,
    alignItems: 'center',
    justifyContent: 'center',
  },
  ringPosition: {
    position: 'absolute',
    alignItems: 'center',
    justifyContent: 'center',
  },
  dataContainer: {
    flex: 1,
    gap: 3,
  },
  dataRow: {
    flexDirection: 'row',
    alignItems: 'center',
    justifyContent: 'space-between',
  },
  dataText: {
    fontSize: 12,
    fontWeight: '700',
    flex: 1,
    fontFamily: 'AliBold',
  },
  dataValue: {
    color: '#192126',
  },
  dataGoal: {
    color: '#9AA3AE',
  },
  dataUnit: {
    fontSize: 10,
    color: '#9AA3AE',
    fontWeight: '500',
    minWidth: 25,
    textAlign: 'right',
    fontFamily: 'AliRegular',
  },
});
