import React, { useState, useEffect } from 'react';
import { Calculator, TrendingUp, AlertCircle, Coins, Award, HelpCircle } from 'lucide-react';

export default function App() {
  // 基礎設定狀態
  const [cardName, setCardName] = useState('比卡超 Vmax (Pikachu Vmax)');
  const [rawCost, setRawCost] = useState(150); // 裸卡成本預設
  const [gradingFee, setGradingFee] = useState(150); // 評級費預設
  
  // 價值預期狀態
  const [value10, setValue10] = useState(2000); // 10分價值
  const [value9, setValue9] = useState(600);    // 9分價值
  const [valueOther, setValueOther] = useState(150); // 8分或以下價值(通常等於裸卡或略低)

  // 機率狀態 (%)
  const [prob10, setProb10] = useState(40);
  const [prob9, setProb9] = useState(50);
  const probOther = 100 - prob10 - prob9;

  // 處理機率變動,確保總和不超過 100%
  const handleProb10Change = (e) => {
    let val = parseInt(e.target.value) || 0;
    if (val < 0) val = 0;
    if (val > 100) val = 100;
    setProb10(val);
    if (val + prob9 > 100) {
      setProb9(100 - val);
    }
  };

  const handleProb9Change = (e) => {
    let val = parseInt(e.target.value) || 0;
    if (val < 0) val = 0;
    if (val > 100) val = 100;
    setProb9(val);
    if (val + prob10 > 100) {
      setProb10(100 - val);
    }
  };

  // 計算結果
  const totalCost = parseFloat(rawCost) + parseFloat(gradingFee);
  
  const profit10 = value10 - totalCost;
  const roi10 = totalCost > 0 ? ((profit10 / totalCost) * 100).toFixed(1) : 0;
  
  const profit9 = value9 - totalCost;
  const roi9 = totalCost > 0 ? ((profit9 / totalCost) * 100).toFixed(1) : 0;

  const profitOther = valueOther - totalCost;
  
  // 期望值 (Expected Value) 計算
  const expectedRevenue = (value10 * (prob10 / 100)) + (value9 * (prob9 / 100)) + (valueOther * (probOther / 100));
  const expectedProfit = expectedRevenue - totalCost;
  const expectedROI = totalCost > 0 ? ((expectedProfit / totalCost) * 100).toFixed(1) : 0;

  // 格式化貨幣顯示
  const formatMoney = (num) => {
    return '$' + parseFloat(num).toLocaleString('en-US', { minimumFractionDigits: 0, maximumFractionDigits: 0 });
  };

  return (
    <div className="min-h-screen bg-slate-50 p-4 md:p-8 font-sans text-slate-800">
      <div className="max-w-6xl mx-auto">
        
        {/* 標題區 */}
        <header className="mb-8 text-center md:text-left">
          <div className="flex items-center justify-center md:justify-start gap-3 mb-2">
            <Award className="w-8 h-8 text-yellow-500" />
            <h1 className="text-3xl font-bold text-slate-900">卡牌評級回報估算機</h1>
          </div>
          <p className="text-slate-500">輸入卡牌成本、預計價值及獲取高分的機率,計算評級的真實期望回報。</p>
        </header>

        <div className="grid grid-cols-1 lg:grid-cols-12 gap-8">
          
          {/* 左側:輸入區 */}
          <div className="lg:col-span-5 space-y-6">
            
            {/* 卡牌基本資料 */}
            <div className="bg-white p-6 rounded-2xl shadow-sm border border-slate-100">
              <h2 className="text-xl font-semibold mb-4 flex items-center gap-2">
                <Calculator className="w-5 h-5 text-blue-500" /> 基本資料及成本
              </h2>
              
              <div className="space-y-4">
                <div>
                  <label className="block text-sm font-medium text-slate-600 mb-1">卡牌名稱</label>
                  <input 
                    type="text" 
                    value={cardName} 
                    onChange={(e) => setCardName(e.target.value)}
                    className="w-full px-4 py-2 bg-slate-50 border border-slate-200 rounded-lg focus:ring-2 focus:ring-blue-500 focus:outline-none transition-all"
                  />
                </div>
                
                <div className="grid grid-cols-2 gap-4">
                  <div>
                    <label className="block text-sm font-medium text-slate-600 mb-1">未評級裸卡成本 ($)</label>
                    <input 
                      type="number" 
                      value={rawCost} 
                      onChange={(e) => setRawCost(e.target.value)}
                      className="w-full px-4 py-2 bg-slate-50 border border-slate-200 rounded-lg focus:ring-2 focus:ring-blue-500 focus:outline-none transition-all"
                    />
                  </div>
                  <div>
                    <label className="block text-sm font-medium text-slate-600 mb-1">評級及運費 ($)</label>
                    <input 
                      type="number" 
                      value={gradingFee} 
                      onChange={(e) => setGradingFee(e.target.value)}
                      className="w-full px-4 py-2 bg-slate-50 border border-slate-200 rounded-lg focus:ring-2 focus:ring-blue-500 focus:outline-none transition-all"
                    />
                  </div>
                </div>
              </div>
            </div>

            {/* 評級後市場價值 */}
            <div className="bg-white p-6 rounded-2xl shadow-sm border border-slate-100">
              <h2 className="text-xl font-semibold mb-4 flex items-center gap-2">
                <Coins className="w-5 h-5 text-yellow-500" /> 評級後市場價值
              </h2>
              
              <div className="space-y-4">
                <div>
                  <label className="block text-sm font-bold text-yellow-600 mb-1">完美 10 分價值 (PSA/BGS 10)</label>
                  <input 
                    type="number" 
                    value={value10} 
                    onChange={(e) => setValue10(e.target.value)}
                    className="w-full px-4 py-2 bg-yellow-50 border border-yellow-200 rounded-lg focus:ring-2 focus:ring-yellow-500 focus:outline-none transition-all font-semibold text-yellow-700"
                  />
                </div>
                <div>
                  <label className="block text-sm font-bold text-slate-500 mb-1">優良 9 分價值 (PSA/BGS 9)</label>
                  <input 
                    type="number" 
                    value={value9} 
                    onChange={(e) => setValue9(e.target.value)}
                    className="w-full px-4 py-2 bg-slate-50 border border-slate-200 rounded-lg focus:ring-2 focus:ring-slate-400 focus:outline-none transition-all font-semibold"
                  />
                </div>
                <div>
                  <label className="block text-sm font-medium text-slate-500 mb-1">8 分或以下價值 (保底價)</label>
                  <input 
                    type="number" 
                    value={valueOther} 
                    onChange={(e) => setValueOther(e.target.value)}
                    className="w-full px-4 py-2 bg-slate-50 border border-slate-200 rounded-lg focus:ring-2 focus:ring-slate-400 focus:outline-none transition-all"
                  />
                  <p className="text-xs text-slate-400 mt-1">通常等同或略低於未評級的裸卡價格。</p>
                </div>
              </div>
            </div>

            {/* 評級機率預估 */}
            <div className="bg-white p-6 rounded-2xl shadow-sm border border-slate-100">
              <div className="flex items-center justify-between mb-4">
                <h2 className="text-xl font-semibold flex items-center gap-2">
                  <TrendingUp className="w-5 h-5 text-indigo-500" /> 評級機率預估
                </h2>
                <div className="group relative">
                  <HelpCircle className="w-5 h-5 text-slate-400 cursor-pointer" />
                  <div className="absolute right-0 w-64 p-3 bg-slate-800 text-white text-xs rounded-lg shadow-xl opacity-0 invisible group-hover:opacity-100 group-hover:visible transition-all z-10 bottom-full mb-2">
                    根據您對卡牌狀態(白邊、置中、暗傷等)的觀察,預估獲得各分數的機率。這會用來計算「期望值」,幫助您作客觀決定。
                  </div>
                </div>
              </div>
              
              <div className="space-y-6">
                <div>
                  <div className="flex justify-between mb-1">
                    <label className="text-sm font-bold text-yellow-600">獲得 10 分機率</label>
                    <span className="text-sm font-bold text-yellow-600">{prob10}%</span>
                  </div>
                  <input 
                    type="range" 
                    min="0" max="100" 
                    value={prob10} 
                    onChange={handleProb10Change}
                    className="w-full h-2 bg-slate-200 rounded-lg appearance-none cursor-pointer accent-yellow-500"
                  />
                </div>

                <div>
                  <div className="flex justify-between mb-1">
                    <label className="text-sm font-bold text-slate-600">獲得 9 分機率</label>
                    <span className="text-sm font-bold text-slate-600">{prob9}%</span>
                  </div>
                  <input 
                    type="range" 
                    min="0" max="100" 
                    value={prob9} 
                    onChange={handleProb9Change}
                    className="w-full h-2 bg-slate-200 rounded-lg appearance-none cursor-pointer accent-slate-500"
                  />
                </div>

                <div className="p-3 bg-slate-50 rounded-lg border border-slate-200 flex justify-between items-center">
                  <span className="text-sm text-slate-500">獲得 8 分或以下機率 (自動計算)</span>
                  <span className="font-medium text-slate-600">{probOther}%</span>
                </div>
              </div>
            </div>

          </div>

          {/* 右側:分析結果區 */}
          <div className="lg:col-span-7 space-y-6">
            
            {/* 總成本顯示 */}
            <div className="bg-slate-900 text-white p-6 rounded-2xl shadow-lg flex flex-col md:flex-row justify-between items-center gap-4">
              <div>
                <p className="text-slate-400 text-sm mb-1">評級總成本 (裸卡 + 評級費)</p>
                <p className="text-3xl font-bold">{formatMoney(totalCost)}</p>
              </div>
              <div className="text-right">
                <p className="text-slate-400 text-sm mb-1">目標卡牌</p>
                <p className="text-xl font-medium text-blue-300">{cardName}</p>
              </div>
            </div>

            {/* 情境分析 */}
            <div className="grid grid-cols-1 md:grid-cols-2 gap-4">
              {/* 情境 A: 10分 */}
              <div className="bg-white p-6 rounded-2xl shadow-sm border-2 border-yellow-200 relative overflow-hidden">
                <div className="absolute top-0 right-0 bg-yellow-100 text-yellow-800 text-xs font-bold px-3 py-1 rounded-bl-lg">
                  完美情境
                </div>
                <h3 className="text-lg font-bold text-slate-800 mb-1">成功獲取 10 分</h3>
                <p className="text-sm text-slate-500 mb-4">回報最豐厚的情況</p>
                
                <div className="space-y-3">
                  <div className="flex justify-between items-center">
                    <span className="text-slate-500 text-sm">預期價值</span>
                    <span className="font-semibold">{formatMoney(value10)}</span>
                  </div>
                  <div className="flex justify-between items-center pb-3 border-b border-slate-100">
                    <span className="text-slate-500 text-sm">總成本</span>
                    <span className="text-red-500 font-medium">-{formatMoney(totalCost)}</span>
                  </div>
                  <div className="flex justify-between items-center">
                    <span className="font-bold text-slate-700">淨利潤</span>
                    <span className={`text-xl font-bold ${profit10 >= 0 ? 'text-green-600' : 'text-red-600'}`}>
                      {profit10 > 0 ? '+' : ''}{formatMoney(profit10)}
                    </span>
                  </div>
                  <div className="flex justify-between items-center pt-2">
                    <span className="text-slate-500 text-sm">回報率 (ROI)</span>
                    <span className={`font-bold px-2 py-1 rounded text-sm ${profit10 >= 0 ? 'bg-green-100 text-green-700' : 'bg-red-100 text-red-700'}`}>
                      {profit10 > 0 ? '+' : ''}{roi10}%
                    </span>
                  </div>
                </div>
              </div>

              {/* 情境 B: 9分 */}
              <div className="bg-white p-6 rounded-2xl shadow-sm border-2 border-slate-200 relative overflow-hidden">
                 <div className="absolute top-0 right-0 bg-slate-100 text-slate-600 text-xs font-bold px-3 py-1 rounded-bl-lg">
                  常見情境
                </div>
                <h3 className="text-lg font-bold text-slate-800 mb-1">獲取 9 分</h3>
                <p className="text-sm text-slate-500 mb-4">較保守的安全網</p>
                
                <div className="space-y-3">
                  <div className="flex justify-between items-center">
                    <span className="text-slate-500 text-sm">預期價值</span>
                    <span className="font-semibold">{formatMoney(value9)}</span>
                  </div>
                  <div className="flex justify-between items-center pb-3 border-b border-slate-100">
                    <span className="text-slate-500 text-sm">總成本</span>
                    <span className="text-red-500 font-medium">-{formatMoney(totalCost)}</span>
                  </div>
                  <div className="flex justify-between items-center">
                    <span className="font-bold text-slate-700">淨利潤</span>
                    <span className={`text-xl font-bold ${profit9 >= 0 ? 'text-green-600' : 'text-red-600'}`}>
                      {profit9 > 0 ? '+' : ''}{formatMoney(profit9)}
                    </span>
                  </div>
                  <div className="flex justify-between items-center pt-2">
                    <span className="text-slate-500 text-sm">回報率 (ROI)</span>
                    <span className={`font-bold px-2 py-1 rounded text-sm ${profit9 >= 0 ? 'bg-green-100 text-green-700' : 'bg-red-100 text-red-700'}`}>
                      {profit9 > 0 ? '+' : ''}{roi9}%
                    </span>
                  </div>
                </div>
              </div>
            </div>

            {/* 期望值大數據總結 */}
            <div className={`p-8 rounded-2xl shadow-md border-2 transition-colors ${expectedProfit >= 0 ? 'bg-emerald-50 border-emerald-200' : 'bg-rose-50 border-rose-200'}`}>
              <div className="flex items-start gap-4">
                <div className={`p-3 rounded-xl ${expectedProfit >= 0 ? 'bg-emerald-100 text-emerald-600' : 'bg-rose-100 text-rose-600'}`}>
                  {expectedProfit >= 0 ? <TrendingUp className="w-8 h-8" /> : <AlertCircle className="w-8 h-8" />}
                </div>
                <div className="flex-1">
                  <h3 className="text-2xl font-bold text-slate-800 mb-2">綜合期望回報 (Expected Value)</h3>
                  <p className="text-slate-600 mb-6 text-sm">
                    這代表如果這張卡牌的狀態在平行時空拿去評級 100 次,結合 {prob10}% 拿十分、{prob9}% 拿九分的機率,您平均每次評級的預計利潤。
                  </p>
                  
                  <div className="grid grid-cols-2 gap-4">
                    <div className="bg-white p-4 rounded-xl shadow-sm">
                      <p className="text-sm text-slate-500 mb-1">預計平均淨利</p>
                      <p className={`text-3xl font-bold ${expectedProfit >= 0 ? 'text-emerald-600' : 'text-rose-600'}`}>
                        {expectedProfit > 0 ? '+' : ''}{formatMoney(expectedProfit)}
                      </p>
                    </div>
                    <div className="bg-white p-4 rounded-xl shadow-sm">
                      <p className="text-sm text-slate-500 mb-1">預計平均回報率</p>
                      <p className={`text-3xl font-bold ${expectedProfit >= 0 ? 'text-emerald-600' : 'text-rose-600'}`}>
                        {expectedProfit > 0 ? '+' : ''}{expectedROI}%
                      </p>
                    </div>
                  </div>

                  <div className="mt-6 pt-4 border-t border-slate-200/60">
                    <p className="font-medium text-slate-800">
                      AI 建議結論: 
                      {expectedProfit > totalCost ? 
                        <span className="text-emerald-600 ml-2">強烈建議評級!期望利潤極高。</span> : 
                      expectedProfit > 0 ? 
                        <span className="text-blue-600 ml-2">值得一試,整體期望值為正數。</span> : 
                        <span className="text-rose-600 ml-2">不建議評級,風險大於回報,建議直接出售裸卡。</span>
                      }
                    </p>
                  </div>
                </div>
              </div>
            </div>

          </div>
        </div>
      </div>
    </div>
  );
}

Reset password

Enter your email address and we will send you a link to change your password.

Get started with your account

to save your favourite homes and more

Sign up with email

Get started with your account

to save your favourite homes and more

By clicking the «SIGN UP» button you agree to the Terms of Use and Privacy Policy
Powered by Estatik