import { Colors } from '@/constants/Colors';
import React, { useMemo } from 'react';
import { StyleSheet, View } from 'react-native';
import Svg, * as SvgLib from 'react-native-svg';

export type RadarCategory = { key: string; label: string };

export type RadarChartSize = 'small' | 'medium' | 'large' | number;

export type RadarChartProps = {
  categories: RadarCategory[];
  values: number[]; // 与 categories 一一对应
  maxValue?: number; // 默认 5
  size?: RadarChartSize; // 组件宽高，默认 medium
  levels?: number; // 网格层数，默认 5
  showGrid?: boolean;
  showLabels?: boolean; // 是否显示指标文字
};

// 预设尺寸配置
const SIZE_CONFIG = {
  small: { size: 116, fontSize: 8, labelOffset: -4, radiusRatio: 0.35 },
  medium: { size: 200, fontSize: 11, labelOffset: 15, radiusRatio: 0.38 },
  large: { size: 280, fontSize: 13, labelOffset: 18, radiusRatio: 0.4 },
};

export function RadarChart({
  categories,
  values,
  maxValue = 5,
  size = 'medium',
  levels = 5,
  showGrid = true,
  showLabels = true
}: RadarChartProps) {
  // 解析尺寸配置
  const config = useMemo(() => {
    if (typeof size === 'number') {
      // 自定义尺寸
      const baseSize = Math.max(80, Math.min(400, size));
      let fontSize = 11;
      let labelOffset = 15;
      let radiusRatio = 0.38;

      // 根据尺寸自适应调整
      if (baseSize < 140) {
        fontSize = 9;
        labelOffset = 12;
        radiusRatio = 0.35;
      } else if (baseSize > 240) {
        fontSize = 13;
        labelOffset = 18;
        radiusRatio = 0.4;
      }

      return { size: baseSize, fontSize, labelOffset, radiusRatio };
    }

    // 预设尺寸
    return SIZE_CONFIG[size] || SIZE_CONFIG.medium;
  }, [size]);

  const { size: actualSize, fontSize, labelOffset, radiusRatio } = config;
  const radius = actualSize * radiusRatio;
  const cx = actualSize / 2;
  const cy = actualSize / 2;
  const count = categories.length;

  const points = useMemo(() => {
    return categories.map((_, i) => {
      const angle = (Math.PI * 2 * i) / count - Math.PI / 2; // 顶部起点
      return {
        angle,
        x: (v: number) => cx + Math.cos(angle) * v,
        y: (v: number) => cy + Math.sin(angle) * v
      };
    });
  }, [categories, count, cx, cy]);

  const valuePath = useMemo(() => {
    const rValues = values.map((v) => Math.max(0, Math.min(maxValue, v)) / maxValue * radius);
    const d = rValues
      .map((rv, i) => `${i === 0 ? 'M' : 'L'} ${points[i].x(rv)} ${points[i].y(rv)}`)
      .join(' ');
    return `${d} Z`;
  }, [values, maxValue, radius, points]);

  const gridPolygons = useMemo(() => {
    const polys: string[] = [];
    for (let l = 1; l <= levels; l++) {
      const r = (radius / levels) * l;
      const p = points.map((p) => `${p.x(r)},${p.y(r)}`).join(' ');
      polys.push(p);
    }
    return polys;
  }, [levels, radius, points]);

  // 检查是否有足够的空间显示文字
  const hasEnoughSpace = actualSize >= 100;

  return (
    <View style={{ width: actualSize, height: actualSize }}>
      <Svg width={actualSize} height={actualSize}>
        <SvgLib.Defs>
          <SvgLib.LinearGradient id="radarFill" x1="0" y1="0" x2="1" y2="1">
            <SvgLib.Stop offset="0%" stopColor={Colors.light.accentGreen} stopOpacity={0.32} />
            <SvgLib.Stop offset="100%" stopColor="#59C6FF" stopOpacity={0.28} />
          </SvgLib.LinearGradient>
        </SvgLib.Defs>

        {showGrid && (
          <SvgLib.G>
            {gridPolygons.map((pointsStr, idx) => (
              <SvgLib.Polygon
                key={`grid-${idx}`}
                points={pointsStr}
                fill="none"
                stroke="rgba(25,33,38,0.12)"
                strokeWidth={1}
              />
            ))}
            {points.map((p, i) => (
              <SvgLib.Line
                key={`axis-${i}`}
                x1={cx}
                y1={cy}
                x2={p.x(radius)}
                y2={p.y(radius)}
                stroke="rgba(25,33,38,0.12)"
                strokeWidth={1}
              />
            ))}
          </SvgLib.G>
        )}

        {showLabels && hasEnoughSpace && categories.map((c, i) => {
          const r = radius + labelOffset;
          const x = points[i].x(r);
          const y = points[i].y(r);
          const anchor = Math.cos(points[i].angle) > 0.2 ? 'start' : Math.cos(points[i].angle) < -0.2 ? 'end' : 'middle';
          const dy = Math.sin(points[i].angle) > 0.6 ? 10 : Math.sin(points[i].angle) < -0.6 ? -4 : 4;

          return (
            <SvgLib.Text
              key={`label-${c.key}`}
              x={x}
              y={y + dy}
              fontSize={fontSize}
              fill="#192126"
              textAnchor={anchor}
            >
              {c.label}
            </SvgLib.Text>
          );
        })}

        <SvgLib.Path d={valuePath} fill="url(#radarFill)" stroke="#A8DB3D" strokeWidth={2} />
        <SvgLib.Circle cx={cx} cy={cy} r={3} fill="#A8DB3D" />
      </Svg>
    </View>
  );
}

const styles = StyleSheet.create({});