import React, { useState, useEffect } from 'react';
import { useNavigate, useLocation } from 'react-router-dom';
import { generateInviteCode, getUserInviteCodes, exchangeUpload, getUserInfo } from '../../api/personal';
import './personalSubpage.css';

const Exchange = () => {
  const navigate = useNavigate();
  const location = useLocation();
  const [inviteCodes, setInviteCodes] = useState([]);
  const [userInfo, setUserInfo] = useState(null);
  const [magicPoints, setMagicPoints] = useState('0'); 
  const [loading, setLoading] = useState(false);
  const [error, setError] = useState(null);

  // 获取用户信息和邀请码列表
  useEffect(() => {
    const fetchData = async () => {
      try {
        setLoading(true);
        const [userData, codes] = await Promise.all([
          getUserInfo(),
          getUserInviteCodes()
        ]);
        setUserInfo(userData);
        setInviteCodes(codes);
      } catch (err) {
        setError(err.message);
      } finally {
        setLoading(false);
      }
    };
    fetchData();
  }, []);

  // 生成邀请码
  const handleGenerateInviteCode = async () => {
    try {
      setLoading(true);
      const newCode = await generateInviteCode();
      setInviteCodes([...inviteCodes, newCode]);
      // 刷新用户信息
      const updatedUser = await getUserInfo();
      setUserInfo(updatedUser);
    } catch (err) {
      setError(err.message);
    } finally {
      setLoading(false);
    }
  };

  const handleExchangeUpload = async () => {
    const points = Number(magicPoints);
    if (!points || points <= 0) {
      setError('请输入有效的魔力值');
      return;
    }
    try {
      setLoading(true);
      await exchangeUpload(points);
      // 刷新用户信息
      const updatedUser = await getUserInfo();
      setUserInfo(updatedUser);
      setMagicPoints('0');
      setError(null);
    } catch (err) {
      setError(err.message);
    } finally {
      setLoading(false);
    }
  };

  const handleBack = () => {
    // 返回个人中心，并携带来源标记
    navigate('/personal', { 
      state: { 
        fromSubpage: true,  // 标记来自子页面
        dashboardTab: location.state?.dashboardTab // 保留Dashboard的标签页状态
      },
      replace: true  // 替换当前历史记录
    });
  };

  if (loading) {
    return <div className="subpage-container">加载中...</div>;
  }

  if (error) {
    return (
      <div className="subpage-container">
        <button className="back-button" onClick={handleBack}>
      返回个人中心
        </button>
        <div className="error">错误: {error}</div>
      </div>
    );
  }

  return (
    <div className="subpage-container">
      <button className="back-button" onClick={handleBack}>
      返回个人中心
      </button>

      <h2 className="page-title">兑换区</h2>
      
      <div className="exchange-section">
        <h3>当前魔力值: {userInfo?.magicPoints || 0}</h3>
        
        <div className="exchange-card">
          <h4>兑换邀请码</h4>
          <p>消耗10魔力值兑换一个邀请码</p>
          <button 
            className="exchange-btn"
            onClick={handleGenerateInviteCode}
            disabled={!userInfo || userInfo.magicPoints < 10}
          >
            兑换邀请码
          </button>
        </div>

        <div className="exchange-card">
          <h4>兑换上传量</h4>
          <p>1魔力值 = 1GB上传量</p>
          <div className="exchange-input-group">
          <input
            type="number"
            value={magicPoints}
            onChange={(e) => {
              // 允许空字符串或有效数字
              const value = e.target.value;
              if (value === '' || !isNaN(value)) {
                setMagicPoints(value);
              }
            }}
            min="1"
            max={userInfo?.magicPoints || 0}
            placeholder="输入要兑换的魔力值"
          />

          <button 
            className="exchange-btn"
            onClick={handleExchangeUpload}
            disabled={
              !magicPoints || 
              Number(magicPoints) <= 0 || 
              !userInfo || 
              Number(magicPoints) > userInfo.magicPoints
            }
          >
            兑换上传量
          </button>
          </div>
        </div>

        {inviteCodes.length > 0 && (
          <div className="invite-code-list">
            <h4>我的邀请码</h4>
            <ul>
              {inviteCodes.map((code, index) => (
                <li key={index}>
                  <span className="code">{code.code}</span>
                  <span className={`status ${code.isUsed ? 'used' : 'available'}`}>
                    {code.isUsed ? '已使用' : '可用'}
                  </span>
                </li>
              ))}
            </ul>
          </div>
        )}
      </div>
    </div>
  );
};

export default Exchange;