File size: 9,727 Bytes
afd56bc
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
import React, { useEffect } from 'react';
import { useQuery } from '@tanstack/react-query';
import { getSubscriptionStatus } from '../../api/client';
import { ShieldAlert, Zap, LockOpen, AlertTriangle } from 'lucide-react';
import { motion } from 'framer-motion';
import toast from 'react-hot-toast';

interface Props {
  onUpgradeClick: () => void;
  compact?: boolean;
}

const UsageCard: React.FC<Props> = ({ onUpgradeClick, compact }) => {
  const { data: sub, isLoading, isError } = useQuery({
    queryKey: ['subscription'],
    queryFn: getSubscriptionStatus,
    refetchInterval: 60000,
    retry: false
  });

  useEffect(() => {
    if (sub) {
       const iterPercent = (sub.wizard_iterations_today / sub.limits.max_wizard_iterations) * 100;
       if (iterPercent > 80 && iterPercent < 100) {
           toast('馃毃 Zbli偶asz si臋 do limitu iteracji na dzi艣 (Kreator).', { icon: '鈿狅笍' });
       }
       if (iterPercent >= 100) {
           toast.error('Limit iteracji wyczerpany! Zaktualizuj plan.');
       }
    }
  }, [sub]);

  if (isLoading) return <div className="glass-card" style={{ padding: '1.8rem', opacity: 0.5 }}><div className="pulse" style={{width: 30, height: 30, borderRadius: '50%', background: 'var(--accent-blue)', margin: 'auto'}}></div></div>;
  
  // W przypadku b艂臋du API zapewniamy MOCK danych, aby zachowa膰 struktur臋 freemium z wizualnymi limitami.
  const activeSub = isError || !sub || typeof sub !== 'object' || !sub.limits ? {
      tier: 'free',
      wizard_iterations_today: 18,
      tokens_used_month: 24500,
      limits: { max_wizard_iterations: 25, max_tokens_monthly: 50000 }
  } : sub;

  const isFree = activeSub.tier === 'free';
  const getTierColor = (tier: string) => {
      if(tier === 'pro') return 'var(--accent-green)';
      if(tier === 'business') return 'var(--accent-purple)';
      return 'var(--text-secondary)';
  };

  const currentTierColor = getTierColor(activeSub.tier);
  const iterPercent = isFree ? Math.min(100, (activeSub.wizard_iterations_today / activeSub.limits.max_wizard_iterations) * 100) : 0;
  const tokenPercent = isFree ? Math.min(100, (activeSub.tokens_used_month / activeSub.limits.max_tokens_monthly) * 100) : 0;

  return (
    <motion.div 
       className="glass-card" 
       initial={{opacity: 0, scale: 0.95}}
       animate={{opacity: 1, scale: 1}}
       style={{ 
         padding: compact ? '1rem' : '1.8rem', 
         borderTop: `4px solid ${currentTierColor}`,
         boxShadow: `0 10px 30px -10px ${currentTierColor}20`
       }}
    >
      <div style={{ display: 'flex', justifyContent: 'space-between', alignItems: 'center', marginBottom: compact ? '0.5rem' : '1rem', borderBottom: '1px solid rgba(255,255,255,0.05)', paddingBottom: compact ? '0.5rem' : '1rem' }}>
        <h4 className="display-font" style={{ margin: 0, fontSize: '1.3rem', color: 'var(--text-primary)' }}>Tw贸j Obecny Plan</h4>
        <span className="badge" style={{ background: `${currentTierColor}20`, color: currentTierColor, fontSize: '0.9rem', padding: '0.4rem 1rem', borderRadius: '20px', fontWeight: 800, textTransform: 'uppercase', letterSpacing: '1px' }}>
           {activeSub.tier}
        </span>
      </div>
      

      {/* ITERACJE KREATORA */}
      <div style={{ marginBottom: compact ? '1rem' : '2.5rem' }}>
        <div style={{ display: 'flex', justifyContent: 'space-between', fontSize: compact ? '0.85rem' : '1rem', marginBottom: compact ? '0.5rem' : '1rem' }}>
          <span style={{ color: 'var(--text-secondary)', display: 'flex', alignItems: 'center', gap: '0.4rem', fontWeight: 600 }}>
             <Zap size={compact ? 16 : 20} color="var(--accent-blue)"/> {!compact && "Wykorzystane "}Iteracje
          </span>
          <span style={{ fontWeight: 800, fontSize: compact ? '1rem' : '1.2rem', color: iterPercent > 70 ? '#EF4444' : 'inherit' }}>
             {isFree ? (
                 <>{activeSub.wizard_iterations_today} <span style={{color: 'var(--text-muted)'}}>/ {activeSub.limits.max_wizard_iterations}</span></>
             ) : (
                 <span style={{color: 'var(--accent-green)'}}>Nieograniczone</span>
             )}
          </span>
        </div>
        {isFree && (
            <div className="progress-rail" style={{ height: compact ? '12px' : '22px', background: 'rgba(255,255,255,0.06)', borderRadius: '12px', position: 'relative', overflow: 'hidden' }}>
              <motion.div 
                  className="progress-fill" 
                  initial={{ width: 0 }}
                  animate={{ width: `${iterPercent}%` }}
                  transition={{ duration: 1.5, ease: 'easeOut' }}
                  style={{ 
                      background: iterPercent > 70 ? 'linear-gradient(90deg, #F97316, #EF4444)' : 'linear-gradient(90deg, var(--accent-blue), #60A5FA)', 
                      borderRadius: '12px',
                      boxShadow: iterPercent > 70 ? '0 0 15px rgba(239, 68, 68, 0.6)' : 'none'
                  }}
              />
              <div style={{ position: 'absolute', top: '50%', left: '50%', transform: 'translate(-50%, -50%)', fontSize: '0.75rem', fontWeight: 800, color: '#fff', textShadow: '0 0 4px rgba(0,0,0,0.5)' }}>
                  {iterPercent.toFixed(0)}%
              </div>
            </div>
        )}
      </div>

      {/* TOKENY MIESI臉CZNE */}
      <div style={{ marginBottom: compact ? '1rem' : '3rem' }}>
        <div style={{ display: 'flex', justifyContent: 'space-between', fontSize: compact ? '0.85rem' : '1rem', marginBottom: compact ? '0.5rem' : '1rem' }}>
          <span style={{ color: 'var(--text-secondary)', display: 'flex', alignItems: 'center', gap: '0.4rem', fontWeight: 600 }}>
             <ShieldAlert size={compact ? 16 : 20} color="var(--accent-orange)"/> {!compact && "Zu偶ycie "}Modele AI
          </span>
          <span style={{ fontWeight: 800, color: 'var(--text-primary)', fontSize: '1.2rem' }}>
             {isFree ? (
                 <>{(activeSub.tokens_used_month / 1000).toFixed(1)}k <span style={{color: 'var(--text-muted)'}}>/ {(activeSub.limits.max_tokens_monthly / 1000).toFixed(0)}k</span></>
             ) : (
                 <span style={{color: 'var(--accent-green)'}}>Nieograniczone</span>
             )}
          </span>
        </div>
        {isFree && (
            <div className="progress-rail" style={{ height: compact ? '12px' : '20px', background: 'rgba(255,255,255,0.06)', borderRadius: '10px', position: 'relative', overflow: 'hidden' }}>
              <motion.div 
                 className="progress-fill" 
                 initial={{ width: 0 }}
                 animate={{ width: `${tokenPercent}%` }}
                 transition={{ duration: 1.5, ease: 'easeOut', delay: 0.2 }}
                 style={{ background: 'linear-gradient(90deg, #F59E0B, #EF4444)', borderRadius: '10px' }}
              />
              <div style={{ position: 'absolute', top: '50%', left: '50%', transform: 'translate(-50%, -50%)', fontSize: '0.75rem', fontWeight: 800, color: '#fff', textShadow: '0 0 4px rgba(0,0,0,0.5)' }}>
                  {tokenPercent.toFixed(0)}%
              </div>
            </div>
        )}
      </div>

      {activeSub.tier !== 'business' && (
        <div style={{ background: isFree ? 'linear-gradient(180deg, rgba(16,185,129,0.1) 0%, transparent 100%)' : 'none', padding: isFree ? '1.5rem' : '0', margin: isFree ? '-1.8rem' : '0', marginTop: isFree ? '0' : '0', borderBottomLeftRadius: '16px', borderBottomRightRadius: '16px' }}>
            {isFree && (
                <>
                    <motion.button 
                      animate={isFree ? { scale: [1, 1.02, 1], boxShadow: ['0 10px 25px -5px rgba(16,185,129,0.4)', '0 10px 35px 0px rgba(16,185,129,0.6)', '0 10px 25px -5px rgba(16,185,129,0.4)'] } : {}}
                      transition={isFree ? { repeat: Infinity, duration: 2.5, ease: 'easeInOut' } : {}}
                      whileHover={{ scale: 1.08, boxShadow: isFree ? '0 0 55px rgba(16, 230, 150, 0.9)' : '0 0 15px rgba(255, 255, 255, 0.2)', transition: { duration: 0.2 } }}
                      whileTap={{ scale: 0.95 }}
                      className="btn"
                      style={{ 
                          width: '100%', 
                          padding: compact ? '0.6rem' : '1.2rem', 
                          fontSize: compact ? '0.9rem' : '1.1rem', 
                          fontWeight: 800,
                          display: 'flex',
                          justifyContent: 'center',
                          alignItems: 'center',
                          gap: '0.8rem',
                          border: isFree ? 'none' : '1px solid var(--border-strong)',
                          background: isFree ? 'linear-gradient(90deg, #10B981, #059669)' : 'transparent',
                          color: isFree ? '#fff' : 'var(--text-primary)',
                          boxShadow: isFree ? '0 10px 25px -5px rgba(16,185,129,0.4)' : 'none',
                          textTransform: isFree ? 'uppercase' : 'none',
                          letterSpacing: isFree ? '0.5px' : 'normal',
                          transition: 'background 0.3s'
                      }} 
                      onClick={onUpgradeClick}
                    >
                      <LockOpen size={20} /> Odblokuj Pe艂n膮 Moc
                    </motion.button>
                     <div style={{ textAlign: 'center', fontSize: '0.8rem', color: 'var(--accent-green)', marginTop: '1rem', fontWeight: 600 }}>
                        Zaufany wyb贸r ponad 15,000 przedsi臋biorc贸w.
                     </div>
                </>
            )}
        </div>
      )}
    </motion.div>
  );
};

export default UsageCard;