import React, { useState, useMemo, useEffect } from 'react';
import { fetchRealData } from '../data/historicalData';
import { mockPortfolios } from '../data/mockData';
import { tickerMetrics } from '../data/tickerMetrics';
import { PieChart, Pie, Cell, ResponsiveContainer, Tooltip } from 'recharts';
import Indicators from '../components/Indicators';
import FeeTransparencyModule from '../components/FeeTransparencyModule';
import RebalancingEngine from '../components/RebalancingEngine';
import TransparencyModal from '../components/TransparencyModal';
import MacroTracker from '../components/MacroTracker';
import StockPopup from '../components/StockPopup';
import PortfolioHeatmap from '../components/PortfolioHeatmap';
import FinancialCalculators from '../components/FinancialCalculators';
import { LayoutGrid, Plus, PieChart as PieIcon, BarChart3, X, ChevronRight } from 'lucide-react';
import { motion, AnimatePresence } from 'framer-motion';
import StockSearch from '../components/StockSearch';
import HoldingsList from '../components/HoldingsList';

export default function Dashboard({ riskProfile }) {
  // Initialize with a cached portfolio if available, otherwise an empty one
  const [currentPortfolio, setCurrentPortfolio] = useState(() => {
    const saved = localStorage.getItem('gs_portfolio');
    if (saved) {
      try {
        return JSON.parse(saved);
      } catch (e) {
        console.error("Error loading saved portfolio:", e);
      }
    }
    return mockPortfolios[riskProfile] || { allocation: [] };
  });

  // Save to cache whenever portfolio changes
  useEffect(() => {
    localStorage.setItem('gs_portfolio', JSON.stringify(currentPortfolio));
  }, [currentPortfolio]);
  const [modalData, setModalData] = useState(null);
  
  // State for popups
  const [activePopupAsset, setActivePopupAsset] = useState(null);
  const [showHeatmap, setShowHeatmap] = useState(false);
  const [isSearchOpen, setIsSearchOpen] = useState(false);
  const [isHoldingsOpen, setIsHoldingsOpen] = useState(false);
  const [totals, setTotals] = useState({ value: 0, change: 0, percent: 0, rawValue: 0, loading: true });
  const [prices, setPrices] = useState({});

  // Dynamic Calculation of Health, Risk, and Weights based on real metrics
  const displayPortfolio = useMemo(() => {
    let totalBeta = 0;
    let totalExpense = 0;
    const numAssets = currentPortfolio.allocation.length;
    
    // Calculate current market total
    let marketTotal = 0;
    currentPortfolio.allocation.forEach(asset => {
      const priceData = prices[asset.ticker] || { price: 0 };
      marketTotal += asset.shares * priceData.price;
    });

    const updatedAllocation = currentPortfolio.allocation.map(asset => {
      const priceData = prices[asset.ticker] || { price: 0, percent: 0 };
      const marketVal = asset.shares * priceData.price;
      const weight = marketTotal > 0 ? (marketVal / marketTotal) * 100 : 0;
      
      const totalCost = asset.shares * (asset.buyPrice || priceData.price);
      const gainLoss = marketVal - totalCost;
      const returnPct = (totalCost > 0 && !isNaN(gainLoss) && isFinite(gainLoss)) ? (gainLoss / totalCost) * 100 : 0;
      
      const metrics = tickerMetrics[asset.ticker] || { beta: 1, expenseRatio: 0.1 };
      totalBeta += (metrics.beta || 1) * (weight / 100);
      totalExpense += (metrics.expenseRatio || 0.1) * (weight / 100);

      return {
        ...asset,
        value: Number(weight.toFixed(2)),
        dayChange: priceData.percent,
        dollarChange: priceData.change,
        returnPct
      };
    });

    if (numAssets === 0) {
      return { 
        ...currentPortfolio,
        healthScore: 0, 
        riskLevel: 'None', 
        avgBeta: '0.00',
        stockSplit: 0,
        mfSplit: 0
      };
    }

    // Determine Risk Level
    let riskLevel = 'Medium';
    if (totalBeta < 0.6) riskLevel = 'Low';
    else if (totalBeta > 1.2) riskLevel = 'High';

    // Determine Health Score (Base 100)
    let healthScore = 100;
    healthScore -= Math.min(totalExpense * 100 * 2, 20);
    if (numAssets >= 5) healthScore += 5;
    
    const profileMap = { 'Cautious': 'Low', 'Balanced': 'Medium', 'Bold': 'High' };
    if (riskLevel !== profileMap[riskProfile]) healthScore -= 15;
    healthScore = Math.min(Math.max(Math.round(healthScore), 0), 100);

    // Calculate Asset Type Split
    let stockWeight = 0;
    let mfWeight = 0;
    updatedAllocation.forEach(asset => {
      if (asset.type === 'mf') mfWeight += asset.value;
      else stockWeight += asset.value;
    });

    return { 
      ...currentPortfolio,
      allocation: updatedAllocation,
      healthScore, 
      riskLevel, 
      avgBeta: totalBeta.toFixed(2),
      stockSplit: stockWeight,
      mfSplit: mfWeight
    };
  }, [currentPortfolio, riskProfile, prices]);

  const handleRebalance = (scenario) => {
    setModalData(scenario);
  };

  const closeModal = () => setModalData(null);
  const closeStockPopup = () => setActivePopupAsset(null);

  const handleAddStock = (newAsset) => {
    setCurrentPortfolio(prev => {
      // If portfolio is empty, the first stock gets 100% allocation
      if (prev.allocation.length === 0) {
        return {
          ...prev,
          allocation: [{ ...newAsset, value: 100 }]
        };
      }

      const scale = (100 - newAsset.value) / 100;
      const updatedExisting = prev.allocation.map(a => ({
        ...a,
        value: Number((a.value * scale).toFixed(2))
      }));
      
      // Ensure sum is exactly 100
      const currentSum = updatedExisting.reduce((acc, a) => acc + a.value, 0) + newAsset.value;
      if (currentSum !== 100 && updatedExisting.length > 0) {
        updatedExisting[0].value += Number((100 - currentSum).toFixed(2));
      }

      return {
        ...prev,
        allocation: [...updatedExisting, newAsset]
      };
    });
  };

  const handleRemoveAsset = (ticker) => {
    setCurrentPortfolio(prev => {
      const updatedAllocation = prev.allocation.filter(a => a.ticker !== ticker);
      
      // Redistribute value to maintain 100%
      if (updatedAllocation.length > 0) {
        const currentSum = updatedAllocation.reduce((acc, a) => acc + a.value, 0);
        const scale = 100 / currentSum;
        updatedAllocation.forEach(a => {
          a.value = Number((a.value * scale).toFixed(2));
        });
        
        // Final adjust for rounding
        const finalSum = updatedAllocation.reduce((acc, a) => acc + a.value, 0);
        if (finalSum !== 100) {
          updatedAllocation[0].value += Number((100 - finalSum).toFixed(2));
        }
      }

      return {
        ...prev,
        allocation: updatedAllocation
      };
    });
  };

  useEffect(() => {
    async function calculateTotals() {
      if (currentPortfolio.allocation.length === 0) {
        setTotals({ value: '$0.00', change: '$0.00', percent: '0.00', isPositive: true, loading: false });
        return;
      }
      
      setTotals(prev => ({ ...prev, loading: true }));
      
      const pricePromises = currentPortfolio.allocation.map(asset => fetchRealData(asset.ticker));
      const results = await Promise.all(pricePromises);
      
      let newTotalValue = 0;
      let newTotalChange = 0;
      const priceMap = {};
      
      results.forEach((data, index) => {
        const ticker = currentPortfolio.allocation[index].ticker;
        priceMap[ticker] = {
          price: data.currentPrice,
          change: data.change,
          percent: (data.change / (data.currentPrice - data.change)) * 100,
          history: data.history
        };
        newTotalValue += currentPortfolio.allocation[index].shares * data.currentPrice;
        newTotalChange += (currentPortfolio.allocation[index].shares * data.change);
      });

      setPrices(priceMap);

      const percent = newTotalValue > 0 ? (newTotalChange / (newTotalValue - newTotalChange)) * 100 : 0;

      // Update totals
      setTotals({
        value: newTotalValue.toLocaleString('en-US', { style: 'currency', currency: 'USD' }),
        change: newTotalChange.toLocaleString('en-US', { style: 'currency', currency: 'USD' }),
        percent: percent.toFixed(2),
        rawValue: newTotalValue,
        isPositive: newTotalChange >= 0,
        loading: false
      });
    }
    calculateTotals();
  }, [JSON.stringify(currentPortfolio.allocation.map(a => `${a.ticker}-${a.shares}`))]);

  return (
    <div className="min-h-screen bg-gs-light p-6 md:p-12 relative">
      <div className="max-w-7xl mx-auto">
        <header className="mb-10 flex flex-col md:flex-row justify-between items-start md:items-end gap-6">
          <div>
            <h1 className="text-3xl md:text-4xl font-light text-gs-navy mb-2">
              Your <span className="font-semibold">{riskProfile}</span> Portfolio
            </h1>
            <p className="text-gs-slate text-lg font-light">
              Built for your goals. Transparently managed.
            </p>
          </div>
          
          <div className="bg-white px-8 py-4 rounded-2xl border border-gray-100 shadow-sm flex items-center gap-8 min-w-[320px]">
            <div>
              <p className="text-[10px] font-bold text-gs-slate uppercase tracking-widest mb-1">Total Value</p>
              {totals.loading ? (
                <div className="h-8 w-24 bg-gray-100 animate-pulse rounded"></div>
              ) : (
                <p className="text-2xl font-bold text-gs-navy">{totals.value}</p>
              )}
            </div>
            <div className="h-10 w-px bg-gray-100"></div>
            <div>
              <p className="text-[10px] font-bold text-gs-slate uppercase tracking-widest mb-1">Day Change</p>
              {totals.loading ? (
                <div className="h-8 w-24 bg-gray-100 animate-pulse rounded"></div>
              ) : (
                <p className={`text-lg font-bold ${totals.isPositive ? 'text-green-600' : 'text-red-500'}`}>
                  {totals.isPositive ? '+' : ''}{totals.change}
                  <span className="text-xs ml-1 font-medium">({totals.isPositive ? '+' : ''}{totals.percent}%)</span>
                </p>
              )}
            </div>
          </div>
        </header>

        {/* Portfolio Overview & Holdings Section */}
        <div className="space-y-8 mb-10">
          {/* Top Landscape "Tablet": Allocation & Summary */}
          <div className="bg-white rounded-[2.5rem] p-10 shadow-xl border border-gray-100 flex flex-col xl:flex-row items-center gap-12 relative overflow-hidden">
            <div className="absolute top-0 right-0 w-64 h-64 bg-gs-gold/5 rounded-full -mr-32 -mt-32 blur-3xl"></div>
            
            {/* Left Column: Chart & Composition */}
            <div className="flex flex-col items-center xl:items-start flex-1 min-w-[320px]">
              <h3 className="text-2xl font-bold text-gs-navy mb-6 flex items-center gap-3">
                <PieIcon className="text-gs-gold" size={24} /> Allocation
              </h3>
              <div className="w-full h-64 mb-8">
                <ResponsiveContainer width="100%" height="100%">
                  <PieChart>
                    <Pie
                      data={displayPortfolio.allocation}
                      cx="50%"
                      cy="50%"
                      innerRadius={85}
                      outerRadius={115}
                      paddingAngle={4}
                      dataKey="value"
                      nameKey="name"
                      stroke="none"
                    >
                      {displayPortfolio.allocation.map((entry, index) => (
                        <Cell key={`cell-${index}`} fill={entry.color} />
                      ))}
                    </Pie>
                    <Tooltip 
                      contentStyle={{ borderRadius: '16px', border: 'none', boxShadow: '0 20px 25px -5px rgba(0, 0, 0, 0.1)' }}
                      formatter={(value) => [`${value}%`, 'Weight']}
                    />
                  </PieChart>
                </ResponsiveContainer>
              </div>
              
              {/* Portfolio Composition moved here under the chart */}
              <div className="w-full max-w-[300px] mt-2">
                <div className="flex justify-between text-[10px] font-bold text-gs-navy uppercase tracking-widest mb-2.5">
                  <span>Equities ({displayPortfolio.stockSplit.toFixed(0)}%)</span>
                  <span>Fixed Income ({displayPortfolio.mfSplit.toFixed(0)}%)</span>
                </div>
                <div className="h-1.5 w-full bg-gray-100 rounded-full overflow-hidden flex shadow-inner">
                  <div className="h-full bg-gs-navy" style={{ width: `${displayPortfolio.stockSplit}%` }}></div>
                  <div className="h-full bg-gs-gold" style={{ width: `${displayPortfolio.mfSplit}%` }}></div>
                </div>
              </div>
            </div>
            
            {/* Right: Strategy, Transparency & Side-by-Side Actions */}
            <div className="flex-[1.5] w-full flex flex-col justify-between space-y-6">
              <div className="space-y-4">
                <div className="bg-gs-navy rounded-[2rem] p-6 text-white relative overflow-hidden shadow-lg border border-white/5">
                  <div className="absolute -right-6 -top-6 w-24 h-24 bg-gs-gold/10 rounded-full blur-2xl"></div>
                  <h4 className="text-[9px] font-bold text-gs-gold uppercase tracking-[0.2em] mb-2.5">Strategy Target</h4>
                  <p className="text-sm font-light leading-relaxed">
                    Portfolio optimized for a <span className="font-bold text-gs-gold">{riskProfile}</span> objective.
                  </p>
                </div>
                
                <FeeTransparencyModule portfolio={displayPortfolio} />
              </div>

              {/* Side-by-Side Action Buttons at the bottom */}
              <div className="grid grid-cols-2 gap-4">
                <button 
                  onClick={() => setIsHoldingsOpen(true)}
                  className="flex items-center justify-center gap-3 py-5 bg-gs-navy text-white rounded-2xl hover:bg-gs-gold hover:text-gs-navy transition-all group shadow-xl shadow-gs-navy/20 active:scale-95 border border-white/5"
                >
                  <BarChart3 size={18} className="group-hover:scale-110 transition-transform" />
                  <span className="font-bold text-xs tracking-tight uppercase">Holdings</span>
                </button>
                <button 
                  onClick={() => setShowHeatmap(true)}
                  className="flex items-center justify-center gap-3 py-5 bg-gs-light text-gs-navy rounded-2xl hover:bg-gs-navy hover:text-white transition-all group active:scale-95 border border-gs-navy/5 shadow-sm"
                >
                  <LayoutGrid size={18} className="group-hover:scale-110 transition-transform" />
                  <span className="font-bold text-xs tracking-tight uppercase">Heatmap</span>
                </button>
              </div>
            </div>
          </div>

          <div className="grid grid-cols-1 md:grid-cols-2 gap-8">
            <Indicators portfolio={displayPortfolio} isFlattened={true} />
          </div>
        </div>

        {/* Investment & Retirement Planning Section */}
        <FinancialCalculators />

        <div className="grid grid-cols-1 xl:grid-cols-3 gap-8 mt-8">
          {/* Rebalancing Engine - Spanning more width since Indicators are above */}
          <div className="xl:col-span-3">
            <RebalancingEngine onScenarioSelect={handleRebalance} />
          </div>
        </div>

        {/* Bottom Section: MacroTracker */}
        <MacroTracker />
      </div>

      <TransparencyModal 
        isOpen={!!modalData} 
        onClose={closeModal} 
        data={modalData} 
        currentPortfolio={displayPortfolio}
        totalValue={totals.rawValue}
        prices={prices}
      />
      
      <StockPopup 
        ticker={activePopupAsset?.ticker} 
        assetName={activePopupAsset?.name} 
        onClose={closeStockPopup} 
        allHoldings={displayPortfolio.allocation}
        prices={prices}
      />
      
      <AnimatePresence>
        {isHoldingsOpen && (
          <div className="fixed inset-0 z-[60] flex items-center justify-center p-4 md:p-10 bg-gs-navy/40 backdrop-blur-md">
            <motion.div 
              initial={{ opacity: 0, scale: 0.9, y: 20 }}
              animate={{ opacity: 1, scale: 1, y: 0 }}
              exit={{ opacity: 0, scale: 0.9, y: 20 }}
              className="w-full max-w-7xl max-h-full overflow-hidden flex flex-col relative"
            >
              <button 
                onClick={() => setIsHoldingsOpen(false)}
                className="absolute top-4 right-6 z-10 p-2 bg-white/10 hover:bg-white/20 text-white rounded-full transition-all backdrop-blur-md border border-white/10"
              >
                <X size={20} />
              </button>
              <div className="overflow-y-auto rounded-[2rem] shadow-2xl">
                <HoldingsList 
                  allocation={displayPortfolio.allocation}
                  prices={prices}
                  onAddClick={() => setIsSearchOpen(true)}
                  onRemoveAsset={handleRemoveAsset}
                />
              </div>
            </motion.div>
          </div>
        )}
      </AnimatePresence>

      <AnimatePresence>
        {showHeatmap && (
          <PortfolioHeatmap 
            onClose={() => setShowHeatmap(false)} 
            allocation={displayPortfolio.allocation} 
          />
        )}
      </AnimatePresence>

      <AnimatePresence>
        {isSearchOpen && (
          <StockSearch 
            isOpen={isSearchOpen} 
            onClose={() => setIsSearchOpen(false)} 
            onAddStock={handleAddStock} 
            currentPortfolio={displayPortfolio}
            totalValue={totals.value}
          />
        )}
      </AnimatePresence>
    </div>
  );
}
